I personally think that a operator>> or operator<< for a class should be able to access the internals of the class, that is, be a friend. You can write it using getters and setters.
Regarding the date-class, I would probably have a "date-time" class that goes to at least minutes (if not seconds).
I would also consider that the date/time is one unit - you don't set the month only. So your set/get function should take all the day, month, year, hour, minute (and second) as parameters. A getter may want to exist to get only month or some such, but for setter, you set all at once.
[But you may not care if the car is picked up at 00:01 and returned at 23:59 on the same day, and thus "free" to rent because it was out "no days", when in fact it was out 23h58m].
I would also recommend that you store the date/time as one integer (e.g. a 64-bit number representing seconds for 1st Jan 2000 or some such). It makes calculating date/time differences (which you probably will need to do if you are doing car-rentals) much easier. If you don't do that, then you will still need a function to either subtract one date from another and give the result in number of days.
--
Mats
Compilers can produce warnings - make the compiler programmers happy: Use them!
Please don't PM me for help - and no, I don't do help over instant messengers.
Is this more like it?
.cppCode:using namespace std; #ifndef DATE #define DATE 1 #endif class Date { public: Date(); ~Date(); Date(int d,int m,int y,int h,int mn,int s); void setTimeDate(int d,int m,int y,int h,int mn,int s); int getDay(); int getMonth(); int getYear(); int getHour(); int getMinute(); int getSecond(); private: int day; int month; int year; int hour; int minute; int second; };
Code:#include "RentalDate.h" Date::Date() { day=month=year=hour=minute=second=0; } Date:: ~Date() {} Date::Date(int d,int m,int y,int h,int mn,int s) { setTimeDate(d,m,y,h,mn,s); } void Date::setTimeDate(int d,int m,int y,int h,int mn,int s) { day=d; month=m; year=y; hour=h; minute=mn; second=s; } int Date::getDay() { return day; } int Date::getMonth() { return month; } int Date::getYear() { return year; } int Date::getHour() { return hour; } int Date::getMinute() { return minute; } int Date::getSecond() { return second; }
While we on date ..
Q.Code:void Menu::setReturnDates(const Date& dates) { int day, month, year; cout << "\nEnter return dates [DAY - MONTH - YEAR]" << endl; cin >> day; cin >> month; cin >> year; dates.setTimeDate(day, month, year, 0, 0, 0); }
1. Should i make Date const, got an error
2. sometimes when i type dates + '.' the members list does not come up (or drop down), should i be worried? I mean is date class visible even in that case? setReturnDates is a member of Menu.Code:error C2662: 'Date::setTimeDate' : cannot convert 'this' pointer from 'const Date' to 'Date &'
You should never have const reference when you intend to call setters.
As Elysia suggested, perhaps you'd like to use default values for the h, m and s parameters so that you don't have to give a bunch of zero's.
--
Mats
Compilers can produce warnings - make the compiler programmers happy: Use them!
Please don't PM me for help - and no, I don't do help over instant messengers.
Because setTimeDate is not const and you can only call const functions from an object that is const. Since a setter can never be const, you should not take the argument by const reference.
Sometimes it screws up. And sometimes it screws up due to an error in your code.2. sometimes when i type dates + '.' the members list does not come up (or drop down), should i be worried? I mean is date class visible even in that case? setReturnDates is a member of Menu.
If it happens, try compiling the current code and fixing the mistakes.
You forgot to change your class definition to match your new implementation.
You made a mistake somewhere.
And a tip for you: name your prototypes exactly as your implementation.
Ie:
void Car::read(istream& indata, Car& car, bool isKeyboard)
And
void read(istream& indata, Car& car, bool isKeyboard);
Makes it more readable.
(As you will see, Visual Studio intellisense gets its information from your definition.)
NOOOO! that was the first, but now got different ones after modifications...
First, modifications
New errors...Code:void Car::read(istream& indata, Car& car, bool isKeyboard) // removed const before car { Date dates; // added indata >> car; if(isKeyboard) { readDates(dates); // changed argument from stream to dates } }
1.
2.Code:// Overload for enum variable when writing data ostream& operator << (ostream& out, Car::TankStatus enumTStatus) { out << reinterpret_cast<int&>(enumTStatus); return out; } // Error 1 : error C2084: function 'std::ostream &operator <<(std::ostream &,Car::TankStatus)' already has a body
i'll pause here...Code:// Ouput the data to screen or file void Car::write(ostream& out, bool isScreen, Date& date) { if(isScreen) // To the output screen { out << setw(6) << make << setw(8) << model; out << setw(10) << yearModel; out << setw(12) << engineCapacity; out << setw(9) << date.day << setw(3) << date.month << setw (5) << date.year; out << setw(13) << getTankStatusName(tankStatus).c_str(); puts(""); } else // To the file { out << " " << make << " " << model; out << " " << yearModel; out << " " << engineCapacity; out << " " << returnDate.day << " " << returnDate.month << " " << returnDate.year; out << " " << tankStatus; } } // Error 2 : error C2511: 'void Car::write(std::ostream &,bool,Date &)' : overloaded member function not found in 'Car'
EDIT: Picked up some of my probs in red, and, am not using getters where am suppose to
Last edited by csonx_p; 07-14-2008 at 04:51 AM.
the function write has no date in the Car declaration, it has in your write function defintion.
Are you sure that you want to cast it to int&?Code:out << reinterpret_cast<int&>(enumTStatus);
Are you sure the problem with operator>> on tankstatus isn't that you are declaring two outputs instead of one input and one output?
--
Mats
Compilers can produce warnings - make the compiler programmers happy: Use them!
Please don't PM me for help - and no, I don't do help over instant messengers.
no, that '&' is not suppose to be there
The errors i'm getting are related to '<<' not '>>'...Are you sure the problem with operator>> on tankstatus isn't that you are declaring two
outputs instead of one input and one output?
I'm not missing any semicolons, please check below..Code:: error C2084: function 'std::ostream &operator <<(std::ostream &,Car::TankStatus)' already has a body error C2264: 'operator <<' : error in function definition or declaration; function not called different error.. TankStatus Car::getTankStatus() { return tankStatus; } syntax error : missing ';' before 'Car::getTankStatus'
Code:// Implementing function to return the name of current status #include "car.h" //#include "Menu.h" using namespace std; Car::Car() {}; std::string Car::getTankStatusName(TankStatus status) { switch (status) { case unknown: return "unknown"; break; case empty: return "Empty"; break; case half: return "Half-Empty"; break; case full: return "Full"; break; default: throw std::runtime_error("Invalid tank status"); return ""; } } void Car::setCarDetails(string carMake, string carModel, unsigned yrModel, unsigned engCap, TankStatus tnkStatus) { make = carMake; model = carModel; yearModel = yrModel; engineCapacity = engCap; tankStatus = tnkStatus; } // Operator < will be used by sort() function bool Car::operator<(const Car& car) const { return make < car.make; } ostream& operator << (ostream& out, Car::TankStatus enumTStatus) { out << reinterpret_cast<int&>(enumTStatus); return out; } istream& operator >> (istream& in, Car::TankStatus& enumTStatus) { int tStatus; in >> tStatus; enumTStatus = reinterpret_cast<Car::TankStatus&>(tStatus); return in; } // Overload for reading input streams istream& operator >> (istream& in, Car& car) { string make, model; int ymodel, engCap; Car::TankStatus ts; in >> make >> model; in >> ymodel; in >> engCap; in >> ts; car.setCarDetails(make, model, ymodel, engCap, ts); } void Car::read(istream& indata, Car& car, bool isKeyboard) { Date dates; indata >> car; if(isKeyboard) { readDates(dates); } } void readDates(Date& dates) { int day, month, year; cout << "\nEnter return dates [DAY - MONTH - YEAR]" << endl; cin >> day; cin >> month; cin >> year; dates.setTimeDate(day, month, year, 20, 59); } // Overload for enum variable when writing data ostream& operator << (ostream& out, Car::TankStatus enumTStatus) { out << reinterpret_cast<int>(enumTStatus); return out; } // Ouput the data to screen or file void Car::write(ostream& out, bool isScreen, Date& date) { if(isScreen) // To the output screen { out << setw(6) << make << setw(8) << model; out << setw(10) << yearModel; out << setw(12) << engineCapacity; out << setw(9) << date.getDay() << setw(3) << date.getMonth() << setw (5) << date.getYear(); out << setw(13) << getTankStatusName(getTankStatus()).c_str(); puts(""); } else // To the file { out << " " << make << " " << model; out << " " << yearModel; out << " " << engineCapacity; out << " " << date.getDay() << " " << date.getMonth() << " " << date.getYear(); out << " " << getTankStatus(); } } // Comparing the user entry with curent record bool Car::sameModel(const std::string& car_model) const { return model == car_model; } string Car::getModel() { return model; } string Car::getMake() { return make; } unsigned Car::getEngineCap() { return engineCapacity; } unsigned Car::getYearModel() { return yearModel; } TankStatus Car::getTankStatus() { return tankStatus; }