1. 默认初始化
#include <iostream>
#include <string>
using namespace std;
class A
{
public:
int m;
string s;
};
int main()
{
A a1;
cout << "----------------------------" << endl;
cout << a1.m << endl;//类内内置类型未定义
cout << a1.s << endl;//string默认初始化为空串
cout << "----------------------------" << endl;
return 0;
}
- 当类中无任何构造函数和类内初始值时,编译器通过合成的默认构造函数来对数据成员进行默认初始化。
- 默认初始化时,变量被赋予的默认值由变量的类型和位置决定,函数体内和类内的内置类型不被初始化,即未定义。
2. 类内初始值(部分编译器不支持)
#include <iostream>
#include <string>
using namespace std;
class A
{
public:
int m = 1;
string s = "a";
};
int main()
{
A a1;
cout << "----------------------------" << endl;
cout << a1.m << endl;
cout << a1.s << endl;
cout << "----------------------------" << endl;
return 0;
}
- 当类中无任何构造函数,但有类内初始值时,编译器在其合成的默认构造函数中,利用类内初始值来初始化数据成员。
3. 构造函数内赋值
#include <iostream>
#include <string>
using namespace std;
class A
{
public:
A() //显式创建的构造函数
{
m = 2;
s = "b";
}
int m = 1;
string s = "a";
};
int main()
{
A a1;
cout << "----------------------------" << endl;
cout << a1.m << endl;
cout << a1.s << endl;
cout << "----------------------------" << endl;
return 0;
}
- 在类内显式创建构造函数,在函数体赋值,其结果会覆盖类内初始值。
- 若成员是const、引用或某种未提供此默认构造函数的类类型时,其成员必须初始化,不能用该方法赋值。
4. 构造函数初始值列表
#include <iostream>
#include <string>
using namespace std;
class B //不含默认构造函数
{
public:
int n;
B(int x) //默认构造函数无参数,此构造函数不是默认构造函数
{
n = x;
}
};
class A
{
public:
A() : m1(10), m2(20), r(m2), b(40) //显示创建的构造函数
{
m1 = 100;
}
int m1 = 1;
const int m2 = 2; //const
const int &r = m1; //引用
B b; //未提供默认构造函数
};
int main()
{
A a1;
cout << "----------------------------" << endl;
cout << a1.m1 << endl;
cout << a1.m2 << endl;
cout << a1.r << endl;
cout << a1.b.n << endl;
cout << "----------------------------" << endl;
return 0;
}
- 若成员是const、引用或某种未提供此默认构造函数的类类型时,其成员必须通过构造函数初始值列表进行初始化。
- 优先级:默认初始化<类内初始值<构造函数初始值列表<构造函数赋值。数据成员的值会被优先级高的值覆盖。
注意:
#include <iostream>
#include <string>
using namespace std;
class B //不含默认构造函数
{
public:
int n;
B(int x, int y) //默认构造函数无参数,此构造函数不是默认构造函数
{
n = x * y;
}
};
class A //类内初始值
{
public:
int m1 = 1;
const int m2 = 2; //const
int &r = m1; //引用
B b = B(3, 4); //未提供默认构造函数
};
int main()
{
A a1;
cout << "----------------------------" << endl;
cout << a1.m1 << " " << a1.m2 << " " << a1.r << " " << a1.b.n << endl;
a1.m1 = 0; //m1是int,可修改
// a1.m2 = 0; //错误,m2是const int,不可修改
a1.r = 5; //r引用m1,对r的修改实际是对m1的修改
a1.b = B(0, 0); //b是类类型,可赋值修改
cout << a1.m1 << " " << a1.m2 << " " << a1.r << " " << a1.b.n << endl;
cout << "----------------------------" << endl;
A a2, a3; //a2.m2和a3.m2不可修改,且总是相等
cout << a2.m2 << endl;
cout << a3.m2 << endl;
cout << "----------------------------" << endl;
return 0;
}
#include <iostream>
#include <string>
using namespace std;
class B //不含默认构造函数
{
public:
int n;
B(int x, int y) //默认构造函数无参数,此构造函数不是默认构造函数
{
n = x * y;
}
};
class A //构造函数初始化列表
{
public:
A() : m1(1), m2(2), r(m1), b(3, 4) {} //默认构造函数
A(int i1, int i2, int x, int y) : m1(i1), m2(i2), r(m1), b(x, y) {} //普通构造函数
int m1;
const int m2; //const
int &r; //引用
B b; //未提供默认构造函数
};
int main()
{
A a1;
cout << "----------------------------" << endl;
cout << a1.m1 << " " << a1.m2 << " " << a1.r << " " << a1.b.n << endl;
a1.m1 = 0; //m1是int,可修改
// a1.m2 = 0; //错误,m2是const int,不可修改
a1.r = 5; //r引用m1,对r的修改实际是对m1的修改
a1.b = B(0, 0); //b是类类型,可赋值修改
cout << a1.m1 << " " << a1.m2 << " " << a1.r << " " << a1.b.n << endl;
cout << "----------------------------" << endl;
A a2(1, 2, 3, 4), a3(10, 20, 30, 40); //a2.m2和a3.m2不可修改,但a2.m2和a3.m2可以不同
cout << a2.m2 << endl;
cout << a3.m2 << endl;
cout << "----------------------------" << endl;
return 0;
}
- 当成员是const、引用或某种未提供此默认构造函数的类类型时,用类内初始值初始化,编译并未报错,程序正常运行。
- 当使用类内初始值初始化const成员时,类的对象无法修改自己的const成员,不同的对象其const成员都是相等的,类内的const与类外的const并无区别。
- 当使用构造函数初始值列表初始化const成员时,类的对象也无法修改自己的const成员,但不同的对象其const成员的值可以不同,符合类的用法。