27、构造函数
#include<iostream.h>
class B
{
public:
B();
B(int);
~B();
void Print() const;
private:
int b;
};
B::B()
{
b = 0;
cout<<"B's default constructor called."<<endl;
}
B::B(int i)
{
b = i;
cout<<"B's constructor called."<<endl;
}
B::~B()
{
cout<<"B's destructor called."<<endl;
}
void B::Print() const
{
cout<<b<<endl;
}
class C:public B
{
public:
C();
C(int i,int j);
~C();
void Print() const;
private:
int c;
};
C::C()
{
c = 0;
cout<<"C's default constructor called."<<endl;
}
C::C(int i,int j):B(i) //构造函数给const、私有成员赋值
{
c = j;
cout<<"C's constructor called."<<endl;
}
C::~C()
{
cout<<"C's destructor called."<<endl;
}
void C::Print() const
{
B::Print();
cout<<c<<endl;
}
void main()
{
C obj(5,6);
obj.Print();
}
总结:a.基类子对象由基类中的构造函数进行初始化;
b.构造函数不能被继承
派生类构造函数的工作:
对自己的数据成员进行初始化;(必须在成员列表中进行)
负责调用基类构造函数使基类的数据成员得以初始化;
调用子对象的构造函数,对派生类中的子对象进行初始化;
析构函数
#include<iostream.h>
class M
{
public:
M();
M(int i,int j);
~M();
void Print();
private:
int m1,m2;
};
M::M()
{
m1 = m2 =0;
}
M::M(int i,int j)
{
m1 = i;
m2 = j;
cout<<"M's constructor called."<<m1<<","<<m2<<endl;
}
M::~M()
{
cout<<"M's destructor called."<<m1<<","<<m2<<endl;
}
void M::Print()
{
cout<<m1<<","<<m2<<",";
}
class N:public M
{
public:
N() { n=0; }
N(int i,int j,int k);
~N();
void Print();
private:
int n;
};
N::N(int i,int j,int k):M(i,j),n(k) //构造函数先调用基类构造函数,然后调用派生类的构造函数。
{
cout<<"N's constructor called."<<n<<endl;
}
N::~N()
{
cout<<"N's Destructor called."<<n<<endl;
}
void N::Print()
{
M::Print();
cout<<n<<endl;
}
void main()
{
N obj1(1,2,3);
N obj2(4,5,6);
obj1.Print();
obj2.Print();
}
总结:a.析构函数的执行顺序与构造函数严格相反:
派生类的析构函数
基类的析构函数
b.派生类构造函数的定义可以省略对基类构造函数的调用,其条件是在基类中必须有
缺省的构造函数或者根本没有定义任何构造函数;(编译器会自动生成构造函数)
c.当基类的构造函数使用一个或多个参数时,派生类必须定义构造函数,提供将参数
传递给基类构造函数的途径;
注意:派生类中构造函数对【基类的构造函数】和自身的【私有成员】赋值。
#include<iostream.h>
class B
{
public:
B();
B(int);
~B();
void Print() const;
private:
int b;
};
B::B()
{
b = 0;
cout<<"B's default constructor called."<<endl;
}
B::B(int i)
{
b = i;
cout<<"B's constructor called."<<endl;
}
B::~B()
{
cout<<"B's destructor called."<<endl;
}
void B::Print() const
{
cout<<b<<endl;
}
class C:public B
{
public:
C();
C(int i,int j);
~C();
void Print() const;
private:
int c;
};
C::C()
{
c = 0;
cout<<"C's default constructor called."<<endl;
}
C::C(int i,int j):B(i) //构造函数给const、私有成员赋值
{
c = j;
cout<<"C's constructor called."<<endl;
}
C::~C()
{
cout<<"C's destructor called."<<endl;
}
void C::Print() const
{
B::Print();
cout<<c<<endl;
}
void main()
{
C obj(5,6);
obj.Print();
}
总结:a.基类子对象由基类中的构造函数进行初始化;
b.构造函数不能被继承
派生类构造函数的工作:
对自己的数据成员进行初始化;(必须在成员列表中进行)
负责调用基类构造函数使基类的数据成员得以初始化;
调用子对象的构造函数,对派生类中的子对象进行初始化;
析构函数
#include<iostream.h>
class M
{
public:
M();
M(int i,int j);
~M();
void Print();
private:
int m1,m2;
};
M::M()
{
m1 = m2 =0;
}
M::M(int i,int j)
{
m1 = i;
m2 = j;
cout<<"M's constructor called."<<m1<<","<<m2<<endl;
}
M::~M()
{
cout<<"M's destructor called."<<m1<<","<<m2<<endl;
}
void M::Print()
{
cout<<m1<<","<<m2<<",";
}
class N:public M
{
public:
N() { n=0; }
N(int i,int j,int k);
~N();
void Print();
private:
int n;
};
N::N(int i,int j,int k):M(i,j),n(k) //构造函数先调用基类构造函数,然后调用派生类的构造函数。
{
cout<<"N's constructor called."<<n<<endl;
}
N::~N()
{
cout<<"N's Destructor called."<<n<<endl;
}
void N::Print()
{
M::Print();
cout<<n<<endl;
}
void main()
{
N obj1(1,2,3);
N obj2(4,5,6);
obj1.Print();
obj2.Print();
}
总结:a.析构函数的执行顺序与构造函数严格相反:
派生类的析构函数
基类的析构函数
b.派生类构造函数的定义可以省略对基类构造函数的调用,其条件是在基类中必须有
缺省的构造函数或者根本没有定义任何构造函数;(编译器会自动生成构造函数)
c.当基类的构造函数使用一个或多个参数时,派生类必须定义构造函数,提供将参数
传递给基类构造函数的途径;
注意:派生类中构造函数对【基类的构造函数】和自身的【私有成员】赋值。