89次浏览

C++ explicit关键字

explicit关键字的作用

表明该构造函数是显示的, 而非隐式的, 类构造函数默认情况下即声明为隐式, explicit关键字只能用于修饰只有一个参数的类构造函数, 由于无参数的构造函数和多参数的构造函数总是显示调用,这种情况在构造函数前加explicit无意义, 且只能用来修饰类的构造函数, 下面我们来看一段代码

#include<iostream>
using namespace std;
class test
{
public:
	test(int n) :i(n){}
	test(){}
private:
	int i;
};
int main()
{
	test t;
	t = 1;//执行成功, 隐式的把1传给了带一个参数的默认构造函数
	return 0;
}

我们可以看到 为什么 “t = 1;” 执行成功了呢?   在C++中, 如果的构造函数只有一个参数时, 那么在编译的时候就会有一个缺省的转换操作: 将该构造函数对应数据类型的数据转换为该类对象. 也就是说 “t = 1;” 这段代码, 编译器自动将整型转换为test类对象, 实际上等同于下面的操作:

test t(1);  
或  
test t(1);  
test t1 = t;

那么我们如何避免这种隐式的转换呢, 用explicit修饰构造函数即可, 再来看看我们修改后的代码

#include<iostream>
using namespace std;
class test
{
public:
	explicit test(int n) :i(n){}
	test(){}
private:
	int i;
};
int main()
{
	test t;
	t = 1;//执行失败, 因为explicit关键字取消了隐式转换  
	return 0;
}

取消隐式转换有什么优点?

google的c++规范中提到explicit的优点是可以避免不合时宜的类型变换,缺点无。所以google约定所有单参数的构造函数都必须是显示的,只有极少数情况下拷贝构造函数可以不声明称explicit。例如作为其他类的透明包装器的类。

例外情况

当除了第一个参数以外的其他参数都有默认值的时候, explicit关键字依然有效, 此时, 当调用构造函数时只传入一个参数, 等效于只有一个参数的类构造函数, 例子如下:

#include<iostream>
using namespace std;
class test
{
public:
	explicit test(int n,int j=0) :i(n){}
	test(){}
private:
	int i;
};

int main()
{
	test t;
	t = 1;//执行失败, 因为第一个参数以外的其他参数都有默认值的时候, explicit关键字依然有效	
	return 0;
}

更多介绍请参考百度或者谷歌, 博主也是翻阅文档, 再根据别人写的一些介绍, 总结出来的。

发表评论

电子邮件地址不会被公开。 必填项已用*标注