rossella lau lecture 10, dco10105, semester b,2005-6 dco10105 object-oriented programming and design...

30
Rossella Lau Lecture 10, DCO10105, Semester B,2005-6 DCO10105 Object-Oriented Programming and Design Lecture 10: Operator overload Operator overload Associate object and reference return Member and non-member operator overload Friend function -- By Rossella Lau

Post on 19-Dec-2015

217 views

Category:

Documents


1 download

TRANSCRIPT

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

DCO10105 Object-Oriented Programming and Design

Lecture 10: Operator overload

Operator overloadAssociate object and reference returnMember and non-member operator overloadFriend function

-- By Rossella Lau

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

The operators can only be applied to basic data types

Basic operators other than . (member identification) and = (assignment) cannot be applied to classes

Some functions are similar to C++ operations, e.g., to check if two objects are equal, to output the contents of an object

Defining those functions as, e.g., equal() or print() are fine but inconsistent with basic data types

C++ supports operator overload to allow for consistency and thus, other flexibilities

A reason for operator overload

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

Forms of operator overload

returnType operatorop(parameter list) [const]

E.g., int operator[](int i) const {return array[i];}

Almost all operators can be overloaded except for . .* :: ?: sizeof with some restrictions (Malik’s slides: 16:8-9)

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

Overloading binary operators

Usually, Arithmetics: e.g.,

TheClass operator+(TheClass const & rhsObject) const Relational: e.g.,

bool operator==(TheClass const & rhsObject) const Compond operators: e.g.,

TheClass & operator+= (TheClass const & rhsObject) I/O operators: e.g.,

ostream & operator<< (ostream & TheClass const & theObject)

rhs – right hand side

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

Operator overload for Complex numbers

A complex number: c = a + bi

Addition of two complex numbers: c3 = c1 + c2 = (a+bi) + (c+di) = (a+c) + (b+d)i

Checking if two complex numbers are equal: c1 = c2 if and only if a == c && b == d

c1 += c2 c1 = (a+c) + (b+d)i

Output in the form of: a + bi

Class Complex { private: double real; double imaginary; public: …… // operator overload: ……};

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

Example of addition and equalComplex operator+ (Complex const & rhs) const { return Complex (getReal() + rhs.getReal(), (getImaginary()+rhs.getImaginary();}bool operator== (Complex const & rhs) const { return getReal() == rhs.getReal() && getImaginary() == rhs.getImaginary();}

To invoke, e.g.,: Complex c1(2,3), c2(3,5), c3;

c3 = c1 + c2;

If (c1 == c2) ……

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

Form of Operator overload execution

One can imagine that internally, C++ interprets the above expressions as: c3 = c1.operator+(c2) and if (c1.operator==(c2))

c1 is the left hand side operand while c2 is the right hand side operand

c1, the object being invoked, does not need to be modified and therefore, the most appropriate prototype should be declared with const

c2, the right hand side object, does not need to be modified and therefore, the most appropriate prototype should be declared as a const reference parameter

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

Example of compound addition

Complex & operator+= (Complex const & rhs) { setReal (getReal() + rhs.getReal()); setImaginary ((getImaginary() + rhs.getImaginary()); return *this;}To invoke, e.g.,:

Complex c1(2,3), c2(3,5);c1 += c2; c1, the object being invoked, or the associate object must be

modified and therefore cannot be declared with const The return data should be the associate object itself and therefore

the return type should be a reference & to reference for the associate object

The associate object is referred to as *this (this is a keyword and is a pointer)

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

Example of insertion operator overload

ostream & (ostream & out, Complex const & complex) { cout << complex.getReal() << “ + ” << complex.getImaginary() << “i” << endl; return out;}To invoke, e.g.,:

Complex c1(2,3);cout << c1;

Note that this operator overload is not a member function of Complex; it must be defined outside the class definition

Imagine the execution form: cout.(c1), the associate object can never be in Complex type

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

Member and non-member operator overload

Some Operator overloads can not be member functions when the left hand side operand is not in the type of the class

Indeed, member operator overload functions can be defined as non member function

E.g., Complex operator+(Complex const & lhs, Complex const & rhs);

There should be two parameters as there is not an associate object

To invoke the non-member operator overload is the same as to invoke a member operator overload function

Malik’s slides: 15:32-33

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

Operator Overloading: Member Versus Nonmember

Certain operators must be overloaded as member functions and some must be overloaded as nonmember (friend) functions

The binary arithmetic operator + can be overloaded either way

Overload + as a member function Operator + has direct access to data members of one of the

objects Need to pass only one object as a parameter

Malik’s slide: 15:32

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

Operator Overloading: Member Versus Nonmember (continued)

Overload + as a nonmember function

Must pass both objects as parameters

Could require additional memory and time to make a local copy of the data

For efficiency purposes, overload operators as member functions

Malik’s slide: 15:33

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

More examples for application bookShop

Add a function operator==() As a member function As a non-member function

Add a function operator<<()

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

Operator overload for Donald’s family

Operations with two different types: Implement deposit() as a member operator+() and a non-

member operator+() Implement withdraw() as a member operator-() and a non-

member operator-()

Implement print() as operator<<()

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

Assignment operator

Remember to overload the assignment operator if there is a pointer data member, otherwise the one generated by the compiler may not be as expected

Malik’s slides: 15:24-25

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

Overloading the Assignment Operator Function Prototype:

const className& operator=(const className&);

Only one formal parameter

Formal parameter is usually a const reference to a particular class

Function return type is a constant reference to a particular class

Malik’s slide: 15:24

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

Overloading the Assignment Operator (continued) Function Definition:

const className& className::operator=(const className& rightObject)

{ //local declaration, if any if (this != &rightObject) //avoid self-assignment { //algorithm to copy rightObject into this object } //Return the object assigned. return *this; } // Malik’s slide: 15:25

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

Operator overload for unary operators

Malik’s slides: 15:26-31, 35

Examples in IntArray: int operator[](int i) const {return array[i];}

int & operator[](int i) {return array[i];}

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

Overloading Unary Operators

To overload a unary operator for a class:

If the operator function is a member of the class, it has no parameters

If the operator function is a nonmember (friend), it has one parameter

Malik’s slide: 15:26

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

Overloading ++ and --

The increment operator has two forms Pre-increment (++u) Post-increment (u++)

u is a variable, say of the type int

Pre-increment: the value of u is incremented by 1 before using u in an expression

Post-increment: the value of u is used in the expression before it is incremented by 1

Malik’s slide: 15:27

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

Overloading the Pre-Increment Operator as a Member Function

Function Prototype:

className operator++();

Function Definition:

className className::operator++()

{

//increment the value of the object by 1

return *this;

} //Malik’s slide: 15:28

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

Overloading the Pre-Increment Operator as a Nonmember Function

Function Prototype:

friend className operator++(className&);

Function Definition:

className operator++(className& incObj)

{

//increment incObj by 1

return incObj;

} // Malik’s slide: 15:29

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

Overloading the Post-Increment Operator as a Member Function

Function Prototype:className operator++(int);

Function Definition:className className::operator++(int u)

{

className temp = *this; //use this pointer to copy

//the value of the object

//increment the object

return temp; //return the old value of the object

} // Malik’s slide: 15:30

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

Overloading the Post-Increment Operator as a Nonmember Function

Function Prototype: friend className operator++(className&, int);

Function Definition: className operator++(className& incObj, int u)

{

className temp = incObj; //copy incObj into temp

//increment incObj

return temp; //return the old value of the object

} // Malik’s slide: 15:31

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

Overloading the Subscript Operator//Overload the operator [] for constant arrays

const Type& className::operator[](int index) const

{

assert(0 <= index && index < arraySize);

return list[index]; //return a pointer of the

//array component

} Malik’s slide: 15:35

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

Friend functions

When defining non-member operator overload functions, if the respective class does not provide accessors or mutators, friend should be declared in the class definition for the overload function

Malik’s slides: 15:11-12

However, it is not preferred, as the purpose of a class is to encapsulate details and hide data from the outside world, one should eliminate using friend function as much as possible

In most of the cases, if a class provides sufficient accessors and mutators, friend functions can be avoided

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

Friend Functions of Classes

friend function: a function defined outside the scope of a class

A friend is a nonmember function

However, has access to private data members

To make a function friend to a class

The reserved word friend precedes the function prototype in the class definition

Malik’s slide: 15:11

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

Friend Functions of Classes (continued)

The word friend appears only in the function prototype (in the class definition), not in the definition of the friend function

When writing the friend definition

The name of the class and the scope resolution operator are not used

Malik’s slide: 15:12

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

Summary

Operator overload provides consistent usage of operators for both basic data types and classes

The associate object of a function is referenced as *thisSometimes, return of a reference object for operator overload

is necessaryOperator overload can be a member or a non member

functionI/O operator overloads cannot be member functionsOperator overload may be required to be a friend function of a

class if it needs to access a private member of the class but friend function can be voided if respective accessors and mutators are defined in the respective class

Rossella Lau Lecture 10, DCO10105, Semester B,2005-6

Reference

Malik: 15.1-7

-- END --