320 likes | 430 Views
Chapter 14: more about classes Static Members. If a member variable is declared static , all objects of that class have access to a single instance of that variable.
E N D
Chapter 14: more about classesStatic Members • If a member variable is declared static, all objects of that class have access to a single instance of that variable. • If a member function is declared static, it may be called before any instances of the class are defined and it may only use static variables.
budget.h – Program #ifndef BUDGET_H #define BUDGET_H class Budget { private: static float corpBudget; float divBudget; public: Budget(void) { divBudget = 0; } void addBudget(float b) { divBudget += b; corpBudget += divBudget; } float getDivBudget(void) { return divBudget; } float getCorpBudget(void) { return corpBudget; } }; // Budget #endif budget.cpp – odd way to initialize float Budget::corpBudget = 250000;
Static Member Functions • The syntax for a static member function is: static <return type><function name>(<parameter list>); • A class’s static member variables come into existence before any instances of the class are created. • The static member functions use only static variables and are callable before any instances of the class are created..
A New budget.h – Program #ifndef BUDGET_H #define BUDGET_H class Budget {private: static float corpBudget; float divBudget; public: … static void mainOffice(float); }; // Budget #endif
budget.cpp – Program #include "budget.h" float Budget::corpBudget = 0; void Budget::mainOffice(float moffice) { corpBudget += moffice; } // Budget::mainOffice
Usingbudget.h– Program #include <iostream.h> #include <iomanip.h> #include "budget.h" void main(void) { float amount; cout << "Enter the main office's budget request: "; cin >> amount; Budget::mainOffice(amount); …
Friends of Classes • A friend is a function that is not a member of a class, but has access to the private members of the class. • The syntax of a friend function is as follows and is included in the .h file for the class: friend <return type><function name>(<parameter type list>);
auxil.h – Program #ifndef AUXIL_H #define AUXIL_H class Budget; // Forward declaration of Budget class class Aux {private: float auxBudget; public: Aux(void) { auxBudget = 0; } void addBudget(float, Budget &); float getDivBudget(void) { return auxBudget; } }; // Aux #endif
budget.h – Program #ifndef BUDGET_H #define BUDGET_H #include "auxil.h" class Budget {private: static float corpBudget; float divBudget; public: Budget(void) { divBudget = 0; } void addBudget(float b) { divBudget += b; corpBudget += divBudget; } float getDivBudget(void) { return divBudget; } float getCorpBudget(void) { return corpBudget; } static void mainOffice(float); friend void Aux::addBudget(float, Budget &); }; // Budget #endif
Friend Classes • As mentioned before, it is possible to make an entire class a friend of another class. • The Budget class could make the Aux class its friend with the following declaration:friend class Aux; • Note – generally a “friend” is bad as it violates the encapsulation principle.
Memberwise Assignment • The = operator may be used to assign one object to another, or to initialize one object with another object’s data. • By default, each member of one object is copied to its counterpart in the other object.
Copy Constructors • A copy constructor is a special constructor, called whenever a new object is created and initialized with another object’s data. • Assume the class Set has a member variable as follows: bool *member which is dynamically allocated. • Consider the following declarations: • Set x(5,15); // 15 possible members, 5 is a member • Set y = x; // Copy constructor is called but – is only a shallow copy, so when set y changes, set x does to
The Default Copy Constructor • If a class doesn’t have a copy constructor, C++ automatically creates a default copy constructor. • The default copy constructor performs a memberwise assignment.
The this Pointer • *this is a special built-in pointer that is available in any member function. • *this contains the address of the object that called the member function. It is the name for ME.
Operator Overloading • C++ allows you to redefine how standard operators work when used with class objects.
Issues of Operator Overloading • You can change an operator’s entire meaning when you overload it. (But don’t.) • You cannot change the number of operands taken by an operator. For example, the + symbol must always be a binary operator. Likewise, ++ and -- must always be unary operators.
Because our unionSet has same arguments and return value as +, we can simply make a name change: Set & Set::operator+(Set & arg2){ Set *res; int min; if(memberMax>arg2.memberMax){ min=arg2.memberMax; res = new Set(*this); } else { res = new Set(arg2); min = memberMax; } for (int i=0; i < min; i++) res->member[i]= arg2.member[i] || member[i]; return *res; };
Overloading the Prefix ++ Operator Set & Set::operator++(void){ bool * member1 = new bool[memberMax+1]; for (int i=0; i < memberMax; i++) member1[i] = member[i]; delete [] member; member = member1; member[memberMax]=false; memberMax++; return *this; }
Overloading the Postfix ++ Operator Set &Set::operator++(int x){// parameter is never used! bool * member1 = new bool[memberMax+1]; for (int i=0; i < memberMax; i++) member1[i] = member[i]; delete [] member; member = member1; member[memberMax]=false; memberMax++; return *this; }
Overloading Relational Operators bool Set::operator<(Set & arg2){// subset for us int min = memberMax; if (arg2.memberMax < min) min = arg2.memberMax; for(int i=0; i <min;i++) if (member[i] && !arg2.member[i]) return false; if (memberMax >min) for (i=min; i < memberMax;i++) if (member[i]) return false; return true; }
Overloading the == Operator bool Set::operator==(Set & arg2){ if (memberMax!=arg2.memberMax) return false; for (int i=0; i < memberMax;i++) if (member[i]!=arg2.member[i]) return false; return true; }
Overloading the << Operator Note – this cannot be a member function of Set as the first argument is not a Set ostream &operator<< ( ostream &strm, Set &obj ) { strm << “Whatever I want”; strm<< “ – but be careful about member variables”; strm << “Since I’m not a member, I can’t access them”; } // operator<<
Overloading the >> Operator istream &operator>> ( istream &strm, Set &obj ) {int ele; strm >> ele; Set.addToSet(x); //or make friend or use input() member } // operator>>
Overloading the [] Operator • In addition to the traditional operators, C++ allows you to change the way the [] (subscript) symbols work.
intarry.h – Program #ifndef INTARRY_H #define INTARRY_H Class IntArray { private: int *aptr; int arraySize; void memError ( void ); void subError ( void ); public: IntArray ( int ); IntArray ( const IntArray & ); ~IntArray ( void ); int size ( void ) { return arraySize }; int &operator[] ( const int & ); }; // IntArray #endif
intarray.cpp – Program IntArray::IntArray ( int s ) { arraySize = s; aptr = new int [s]; if ( aptr == NULL ) memError(); for ( int count = 0; count < arraySize; count++ ) *( aptr + count ) = 0; } // IntArray::IntArray IntArray::IntArray ( const IntArray &obj ) { arraySize = obj.arraySize; aptr = new int [arraySize]; if ( aptr == NULL ) memError(); for ( count = 0; count < arraySize; count ++ ) *( aptr + count ) = *( obj.aptr + count ); } // IntArray::IntArray
intarray.cpp – Program (cont) IntArray::~IntArray ( void ) { if ( arraySize > 0 ) delete [] aptr; } // IntArray::~IntArray void IntArray::memError ( void ) { cout << "ERROR: Cannot allocate memory.\n"; exit( 1 ); } IntArray::memError
intarray.cpp – Program (cont) void IntArray::subError ( void ) { cout << "ERROR: Subscript out of range.\n"; exit( 1 ); } // IntArray::subError int &IntArray::operator[] ( const int &sub ) { if ( sub < 0 || sub > arraySize ) subError(); return aptr[sub]; } // IntArray::operator[]
Object Conversion via overloading • Special operator functions may be written to convert a class object to any other type. FeetInches::operator float ( void ) { float temp = feet; temp += (inches / 12.0); return temp; } // FeetInches::operator float
Note: • No return type is specified in the function header for the previous example. • Because it is a FeetInches-to-float conversion function, it will always return a float.