类的构造函数

来源:互联网 发布:卷皮和淘宝哪个更好 编辑:程序博客网 时间:2024/05/17 09:21

构造函数

类通过一个或几个特殊的成员函数来控制其对象的初始化过程,这些函数叫做构造函数constructor。构造函数的任务是初始化类对象的数据成员,无论何时,只要类的对象被创建,就会执行构造函数。


类通过一个特殊的构造函数来控制默认初始化过程,这个函数叫做默认构造函数default constructor。默认构造函数无须任何实参。

如果我们的类没有显示的定义构造函数,那么编译器将会为我们隐式地定义一个默认构造函数。


编译器创建的构造函数有被称为合成的默认构造函数,按照以下规则初始化类的数据成员。

○如果存在类内的初始值,用它来初始化成员。

类内初始值是c++11新标准中允许的,可以为数据成员提供一个类内初始值(in-class initializer)。创建对象时,类内初始值将用于初始化数据成员。

○否则,默认初始化。


类不能依赖于合成的默认构造函数(本段的关键是不能依赖于编译器为我们生成的默认构造函数,而应该自己定义)

1、只有在类中没有其他任何构造函数时,编译器才会为我们生成一个默认的构造函数。一旦我们定义了一些其他的构造函数,那么除非我们再定义一个默认的构造函数,否则类将没有默认构造函数。

2、对于某些类来说,合成的默认构造函数可能执行错误的操作。定义在块中的内置类型或复合类型(比如数组和指针)执行默认初始化,它们的值将是未定义的。含有内置类型或复合类型成员的类应该在类的内部初始化,或者定义一个自己的默认构造函数。

3、编译器无法为某些类生成一个默认的构造函数。比如类中包含一个其他类类型的成员且这个成员的类型没有默认构造函数,那么编译器将无法初始化该成员。对于这样的类来说,我们必须自定义默认构造函数


类通常应该定义一个默认构造函数

为了示例需要默认构造函数的情况,假定一个NoDefault类,它没有定义自己的默认构造函数,却有一个接受string实参的构造函数。因为该类定义了一个构造函数,因此编译器将不合成默认构造函数。NoDefault类没有默认构造函数,意味着:

1)具有NoDefault成员的每个类的每个构造函数都必须传入一个string值

2)NoDefault类型不能用作动态分配数组的元素类型。

3)NoDefault类型的静态分配数组必须为每个元素提供一个显式的初始化式。


Sales_data() = default;

因为该构造函数不接受任何参数,所以它是一个默认构造函数。我们定义这个构造函数的目的仅仅是我们既需要其他形式的构造函数,又需要默认的构造函数。我们希望这个函数的作用完全等同于之前使用的合成默认构造函数

c++11标准中,=default来要求编译器生成构造函数。之所以有效是因为我们为内置类型的数据成员提供了类内初始值。如果编译器不支持类内初始值,那么应该使用构造函数初始值列表来初始化类的每个成员。


例子

不使用c++11标准

class demo{

private:

int num;

public:

demo(){}

void show(){cout<<num<<endl;}

}

demo d;

d.show();//结果将是未定义的,我的编译器的结果是-1077332384


int num使用类内初始值时,比如int num = 10;

则在支持类内初始值的编译器中输出为10



//数据成员

string bookNo;

unsigned units_sold = 0;

double revenue = 0.0;

该构造函数不接受任何参数,所以是一个默认构造函数。我们定义这个 默认构造函数的目的仅仅是因为我们既需要其他形式的构造函数,也需要默认构造函数。

=default要求编译器来生成默认构造函数。 放在类内部,在默认构造函数是内联的,否则不是内联的。

同样,我们也可以不使用合成默认构造函数,自己编写默认构造函数

Sales_data() :units_sold(0),revenue(0.0),bookNo(""){}


该默认构造函数之所以是有效的,是因为我们为内置类型的数据成员提供了初始值。如果你的编译器不支持类内初始值,那么你的默认构造函数就应该使用构造函数初始值列表来初始化每个成员。


构造函数初始值列表

构造函数初始值列表以一个冒号开始,接着是一个以逗号分隔的数据成员列表,每个数据成员后面接一个放在圆括号中的初始化式。

Sales_data(const string &s): bookNo(s) { }

只有一个string参数的构造函数,对于units_sold,revenue没有显示初始化,它将以合成默认构造函数相同的方式隐式初始化,

Sales_data(const string &s): bookNo(s) ,units_sold(0), revenue(0.0) { }


没有出现在构造函数初始值列表中的成员将通过相应的类内初始值(如果存在的话)初始化,或者执行默认初始化。


复制构造函数



0 0
原创粉丝点击