C++初阶——类和对象(Part5):初始化列表 + static成员

目录

一、初始化列表

1、什么是初始化列表?

2、为什么要初始化列表?

3、注意事项

4、explicit 关键字 

二、static成员

1、static 成员变量

(1)为什么要在类外初始化?

(2)为什么静态成员为所有类对象所共享,不属于某个对象?

2、static 成员函数

(1)为什么静态成员函数不能访问非静态成员变量?

(2)静态成员函数可以调用非静态成员函数吗?

(3)非静态成员函数可以调用类的静态成员函数吗?


一、初始化列表

1、什么是初始化列表?

初始化列表是一个类成员初始化的地方,也是构造函数的一部分,它位于构造函数的形参表和函数体之间;它以一个冒号开始,接着是一个以逗号分隔的数据成员列表,每个"成员变量"后面跟一个放在括号中的初始值或表达式。

class Date
{
public:
	Date()
		:_pi((int*)malloc(sizeof(int) * 5))
		,_a(1)
		,_ch('a')
	{
		//...
	}
private:
	int _a;
	int* _pi;
	char _ch;
};

2、为什么要初始化列表?

在类域私有的地方,那些类的私有成员变量都只是声明,并没有被初始化。所以当类被实例化之后,类里面的成员变量都是随机值。因此,类里面的私有成员必须要有一个地方给它们初始化——那就是初始化列表。

而且,像引用、const、自定义类型(没有默认构造函数)这种一被定义就要被初始化的类型就一定要在初始化列表初始化。

3、注意事项

在初始化列表中初始化成员变量也是存在先后顺序的。但其顺序并不一定是从上至下,而是根据成员变量在私有类域的声明顺序。因此,我们在初始化成员变量时应该与成员的声明顺序保持一致,否则可能会引起某个变量是随机值。

class Date
{
public:
	Date()
		:_pi((int*)malloc(sizeof(int) * 5)) //然后初始化
		,_a(1) //首先初始化
		,_ch('a') //最后初始化
	{
		//...
	}
private:
	int _a;
	int* _pi;
	char _ch;
};

4、explicit 关键字 

当初始化变量时右值与左值的类型不同是,编译器会先生成一个临时变量并把右值的数据按字节拷到这个临时变量里,然后再把这个临时变量的数据赋值给左值。这就是隐式类型转换。

而 explicit 的意义就在于用explicit修饰构造函数,将会禁止单参构造函数的隐式类型转换。 

class Date
{
public:
	explicit Date(int year)
		:_a(year)
		,_pi((int*)malloc(sizeof(int) * 5))
		,_ch('a')
	{
		
	}

private:
	int _a;
	int* _pi;
	char _ch;
};

int main()
{
	Date d1 = 2023;
	return 0;
}

二、static成员

1、static 成员变量

(1)为什么要在类外初始化?

用 static 修饰的成员变量为静态成员变量。它并不在栈上,而是存在了静态区。但我们知道,当类实例化成对象时是在栈上实例化的,然而 static 修饰的变量却不在栈,因此 static 修饰的变量并不能被构造函数初始化,因此只能在类外初始化了。

但初始化的时候就要注意了,因为 static 修饰的成员变量已经在类里声明了,因此在初始化时就不用再在最前面加 static 修饰了,取而代之的是要在变量名前面加类型名和类名限定。

(2)为什么静态成员为所有类对象所共享,不属于某个对象?

在(1)中说了由于静态成员的存储位置是静态区,而不是栈,那么它自然就不属于某个对象了,但由于它在类中声明了,因此它是属于类的而不是属于对象的。同时也正是由于静态成员是属于类的,所以它遵守权限访问。

class Date
{
public:
	Date(int year)
		:_pi((int*)malloc(sizeof(int) * 5))
		,_ch('a')
	{
		this->_a++;
	}

private:
	static int _a;
	int* _pi;
	char _ch;
};

int Date::_a = 10;

int main()
{
	Date d1 = 2023;
	return 0;
}

2、static 成员函数

(1)为什么静态成员函数不能访问非静态成员变量?

在 C++ 中,静态成员函数有一个十分重要的性质,就是没有隐含的 this 指针,因此无法访问非静态成员变量。

(2)静态成员函数可以调用非静态成员函数吗?

答:不可以。由于静态成员函数没有 this 指针,因此是不能通过 this 指针来访问成员函数,但如果在静态成员函数里创建了一个新的对象,那么是可以通过这个对象访问成员函数的。

(3)非静态成员函数可以调用类的静态成员函数吗?

答:可以。因为静态成员函数是属于类的,因此非静态成员函数是可以调用静态成员函数的,只不过调用时要制定类域。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

胎粉仔

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值