Document 7663704

Download Report

Transcript Document 7663704

Working with Classes
A method dealing with two objects
C++ has a pointer which call this .
It gives the address of an object.
Suppose we have two objects of
BankAccount class and we want to know
which one has more balance.
Solution :
Have a method that returns a reference to
the object with larger balance.
Header file for BankAccount class
#ifndef BANK1_H
#define BANK1_H
class BankAccount {
private :
double balance; string name;
public :
BankAccount();
BankAccount(double initial_balance);
void deposit (double amount);
void withdraw (double amount );
double getBalance();
const BankAccount & topval( const BankAccount & s) const;
~BankAccount();
};
#endif
CPP file
#include<iostream.h>
#include “bank1.h”
BankAccount :: BankAccount()
{
balance = 0;
}
BankAccount :: BankAccount(double initialBalance, string
str)
{
balance = initialBalance;
name=str;
}
void BankAccount ::deposit(double amount
{
balance =balance+amount ;
}
void BankAccount::withdraw(double amount)
{
if ( amount > balance )
amount=0;
else
balance=balance-amount;
}
double BankAccount :: getBalance()
{
return balance;
}
BankAccount :: ~BankAccount()
{
cout<<“good bye”;
}
const BankAccount & BankAccount :: topval(
const BankAccount & s) const
{
if (s.balance > balance)
return s;
else
return *this;
}
/* const in parenthesis says that the
function won’t modify the explicitly
accessed object */
/* the const after parenthesis says that the
function won’t modify the implicitly
accessed objects*/
The function returns a reference to one of
the two const objects has to be constant.
top=account1.topval(account2);
Operator Overloading
Like function overloading we can have
operator overloading.
We have already used operator overloading
we use * for multiplication and * for pointer.
C++ allows user to overload operators.
Suppose we want to overload “+” to add two
arrays.
for(int i=0; i<20;i++)
Array3[i]=Array1[i]+Array2[i];
// add element by element
We can define a class that overload + so we
can have
Array3=Array1+Array2;
To overload an operator we use a special
function call.
operatorop(arguments-list);
here op is a operator known for C++.
For example:
operator+(); // overload +
operator@();
// error @ is not a C++ operator
#ifndef MYTIME0_H_
#define MYTIME0_H_
class Time
{
private:
int hours; int minutes;
public:
Time();
Time(int h, int m);
void AddMin(int m);
void AddHr(int h);
void Reset(int h , int m);
Time Sum (const Time &t) const ;
void Show();
};
#endif
#include<iostream>
#include “mytime0.h”;
Time :: Time()
{
hours=minutes=0;
}
Time::Time(int h, int m)
{
hours=h; minutes=m;
}
void Time::AddMin(int m)
{
minutes+=m;
hours+=minutes/60;
minutes %=60;
}
void Time::AddHr(int h)
{
hours+=h;
}
void Time::Reset(int h, int m)
{
hours=h;
minutes=m;
}
Time Time::Sum(const Time &t) const
{
Time sum;
sum.minutes=minutes+t.minutes;
sum.hours=hours+t.hours+sum.minutes/60;
sum.minutes %=60;
return sum;
}
void Time:: Show()
{
cout<<hours<<“hours ,” <<minutes<<“
minutes”;
}
#include<iostream>
#include “mytime0.h”;
int main()
{
Time coding(2,40);
Time fixing(5,55);
Time total;
total=coding.Sum(fixing);
total.Show();
return 0;
}
#ifndef MYTIME0_H_
#define MYTIME0_H_
class Time
{
private:
int hours; int minutes;
public:
Time();
Time(int h, int m);
void AddMin(int m);
void AddHr(int h);
void Reset(int h , int m);
Time operator+(const Time &t) const;
Time operator *(double mult) const;
void Show();
};
#endif
#include<iostream>
#include “mytime0.h”;
Time :: Time()
{
hours=minutes=0;
}
Time::Time(int h, int m)
{
hours=h; minutes=m;
}
void Time::AddMin(int m)
{
minutes+=m;
hours+=minutes/60;
minutes %=60;
}
void Time::AddHr(int h)
{
hours+=h;
}
void Time::Rese(int h, int m)
{
hours=h;
minutes=m;
}
Time Time::operator+(const Time &t) const
{
Time sum;
sum.minutes=minutes+t.minutes;
sum.hours=hours+t.hours+sum.minutes/60;
sum.minutes %=60;
return sum;
}
Time Time::operator*(double mult) const
{
Time result;
long totalmin=hours*mult*60+minutes*mult;
result.hours=totalmin/60;
result.minutes =totalmin % 60;
return result;
}
void Time:: Show()
{
cout<<hours<<“hours ,” <<minutes<<“ minutes”;
}
#include<iostream>
#include “mytime0.h”;
int main()
{
Time coding(2,40);
Time fixing(5,55);
Time total;
total=coding+fixing;
total.Show();
Time morefixing(3,28);
total=morefixing.operator+(total);
total.Show();
total=morefixing* 2.5;
total.Show();
return 0;
}
Time t1,t2,t3,t4;
t4=t1+t2+t3;
t4=t1.operator+(t2+t3);
t4=t1. operator+(t2.operator+(t3));
Overloading Restriction
• Should preserve the syntax for the original
operator.
Time test,
%test /// invalid
We can’t create new operator symbols like
operator **();
We can’t overload the following operators :
sizeof . :: ?:
Operators can be overloaded
+
-
>
*
/
%
^
+= -=
!
=
%=
^=
&= |=
<< &&
()
[]
new ->
--
delete
= Assignment
() Function call
[ ] Subscripting
-> class member access by pointer
Can be overloaded only by member
function.
Friend Function
When a function f is a friend of a class,
f has the same access to class as a function
member has.
We could write :
Time A,B;
A=B*2.5 ; // A=B.operator*(2.5);
But not
A=2.5*B;
Creating a Friend function
friend Time operator*( double m, const Time &t);
Place it in the class declaration.
Time operator*(double m, const Time &t)
{
Time result;
long totalmin=t.hours*m*60+t.minutes*m;
result.hours=totalmin/60;
result.minutes =totalmin % 60;
return result;
}
A=2.5*B;
Is
A=operator*(2.5,B);
Time operator*(double m, const Time &t)
{
return t*m;
}
Overload <<
We want to have
Time t;
cout<<t; instead of t.Show();
both cout and t are objects.
If we want to overload << with a member function
then we should write t<<cout; //odd
Add
friend void operator<<(ostream &os ,const Time
&t);
Then the body :
void operator<<(ostream &os ,const Time &t)
{
os<<t.hours<<“ hours, “<<t.minutes<<“minutes”;
}
• Can we write
cout<< “ time “ << t<< “ Tuesday \n”; ??
No
“ Note that cout<<x; return an object cout of class
ostream”;
int x,y;
cout<<x<<y;
we have
(cout<<x) <<y;
ostream & operator<<(ostream &os ,const Time
&t)
{
os<<t.hours<<“hours,“<<t.minutes<<“minutes”;
return os;
}
Type Casting for Classes
When we write
long count=8;
double time=11;
we have conversion automatically.
#ifndef STONEWT_H_
#define STONEWT_H_
class Stonewt
{
private:
enum{lbs_per_stn=14};
int stone;
double pds_left;
double pounds;
public:
Stonewt(double lbs);
Stonewt(int stn, doub lbs);
Stonewt();
~Stonewt();
void show_lbs() ;
void show_stn();
};
#endif;
#include<iostream>
#include “stonewt.h”;
Stonwt::Stonewt(double lbs)
{
stone=int(lbs) / lbs_per_stn;
pds_left=int(lbs)%lbs_per_stn+lbs-int(lbs);
pounds=lbs;
}
Stonewt::Stonewt(int stn, double lbs)
{
stone=stn;
pds_left=lbs;
pounds=stn*lbs_per_stn+lbs;
}
Stonewt::Stonewt()
{
stone=0;
pound=pds_left=0.0;
}
void Stonewt::show_stn()
{
cout<<stone<<“ stone ,“ <<pds_left<<“ pounds\n”;
}
void Stonewt::show_lbs()
{
cout<<pounds<<“ pounds\n”;
}
now we can write
Stonewt mycat;
mycat=19.6;
this conversion automatically happen and is
implicit conversion.
// it can lead to unexpected conversion
In order to make a conversion explicit we
can write
explicit Stonewt(double lbs);
Stonewt mycat;
mycat=19.6 // is not valid
mycat=Stonewt(19.6);
Can we convert an object to double ?
Yes, but not using constructors. We can use
conversion function.
#ifndef STONEWT_H_
#define STONEWT_H_
class Stonewt
{
private:
enum{lbs_per_stn=14};
int stone;
double pds_left;
double pounds;
public:
Stonewt(double lbs);
Stonewt(int stn, double lbs);
Stonewt(); ~Stonewt();
void show_lbs() ;
void show_stn();
operator int() const;
operator double() const;
};
#endif;
Stonewt::operator int() const
{
return int (pounds+0.5);
}
Stonewt::operator double() const
{
return pounds;
}
We can write :
Stonewt poppins(9,2.8);
double p_wt= poppins; //implicit
cout<<p_wt<<endl;
cout<<int( poppins);