一个自定类: class empty{};
其实等于以下代码:
class Empty {
public:
Empty() { }//default 构造函数
~Empty() { }//析构函数
Empty(const Empty& rhs) { }//copy构造函数
Empty& operator=(const Empty& rhs) { }//copy assignment操作符
};
以下三种情况出现时,会调用一个类的拷贝构造函数:
1) 用一个已经实例化了的该类对象,去实例化该类的另外一个对象;
2) 用该类的对象传值的方式作为一个函数的参数;
3) 一个函数返回值为该类的一个对象。
//
#include "stdafx.h"
#include <iostream>
using namespace std;
{
public:
myClass():a(1),b(1){}
myClass(int m, int n)
{
a = m;
b = n;
}
myClass(myClass& x)
{
a = x.a;
b = x.b;
cout << "copy constructor is called." << endl;
}
friend int someFun1(myClass x);
friend myClass someFun2(int a, int b);
private:
int a;
int b;
};
int fun1(myClass x)
{
return x.a + x.b;
}
{
myClass ca(a, b);
return ca;
}
int _tmain(int argc, _TCHAR* argv[])
{
myClass a;//调用已经声明的构造函数
myClass c(10, 10);
myClass d(c); // 情况1)
int anInt = fun1(c); // 情况2
myClass e = fun2(11, 11); // 情况3
return 0;
}
拷贝构造函数的作用就是用一个已经实例化了的该类对象,去实例化该类的另外一个对象。
// 定义控制台应用程序的入口点。
//
#include "stdafx.h"
#include <iostream>
using namespace std;
class BaseClass {
private:
int a;
public:
BaseClass(int b){a = b;}
void SetValue(int a){this->a = a;}
void Show(){cout << a << endl;}
};
int _tmain(int argc, _TCHAR* argv[]) {
BaseClass base(100);
BaseClass dev = base; // 调用了缺省的隐式拷贝构造函数
BaseClass bc(dev); // 调用了缺省的隐式拷贝构造函数
dev.Show(); // 输出应该是100
dev.SetValue(90);
dev.Show(); // 输出应该是90
base.Show(); // 输出应该是100
bc.Show(); // 输出应该是100
return 0;
}
注意,编译器产出的析构函数是个non-virtual(见条款7),除非这个class的base class自身声明有virtual析构函数(这种情况下这个函数的虚属性。
#include "stdafx.h"
#include <iostream>
using namespace std;
class Person {
public:
Person(string& a, const int& b)
: name(a), id(b) { }
private:
const int id;
string& name;
};
int _tmain(int argc, _TCHAR* argv[]) {
Person p1(string("chu"), 1);
Person p2(string("jun"), 2);
p1 = p2;/// error C2582: 'operator =' function is unavailable in 'Person'
system("pause");
return 0;
}
还有一种情况编译器不会生成copy assignment函数,就是基类型将copy assignment声明为private,派生类型就无法获得编译器的帮助。因为派生类型无法调用基类型的copy assignment函数(不具备访问权限)。
#include "stdafx.h"
#include <iostream>
using namespace std;
class BaseClass {
private:
BaseClass& operator=(const BaseClass& rhs) { }
};
class derived : public BaseClass { };
int _tmain(int argc, _TCHAR* argv[]) {
BaseClass px1, px2;
px1 = px2; / 'BaseClass::operator =' : cannot access private member declared in class 'BaseClass'
system("pause");
return 0;
}
经过以上讲解,想必大家已经对这四个default构造函数,copy构造函数,copy assignment操作符,以及析构函数的概念已经有足够的清晰了~所以请记住编译器可以暗自为class创建default构造函数,copy构造函数,copy assignment操作符,以及析构函数。