C++ 中的默认与隐式构造函数
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/12340257/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Default vs. Implicit constructor in C++
提问by Jan Turoň
This is very trivial, but Czech language (my native) doesn't distinguish between implicit and default, so I am confused by some Czech translations what is the difference between implicit and default constructor or constructor call.
这很简单,但捷克语(我的母语)不区分隐式和默认,所以我对一些捷克语翻译感到困惑,隐式和默认构造函数或构造函数调用之间的区别是什么。
struct Test {
Test(int n=0) { }
};
Can you describe in these terms what is:
你能用这些术语描述什么是:
- Test t1;
- Test t2();
- Test t3 = 3;
- Test t4(4);
- Test t5 = Test(5);
- 测试 t1;
- 测试 t2();
- 测试 t3 = 3;
- 测试 t4(4);
- 测试 t5 = 测试(5);
?
?
回答by David Rodríguez - dribeas
The terms defaultand implicit, when talking about a constructor have the following meaning:
术语default和implicit,在谈论构造函数时具有以下含义:
default constructoris a constructor that can be called with no arguments. It either takes no arguments or has default values for each of the arguments taken.
implicit constructoris a term commonly used to talk about two different concepts in the language, the
implicitly declared constructorwhich is a defaultor copy constructor that will be declared for all user classes if no user defined constructor is provided (default) or no copy constructor is provided (copy). That is, a class with no constructors declared by the user has one default constructorimplicitly declared.
implicitly defined constructoris a implicitly declared constructorthat is used (odr-used1in the language and for which the compiler will provide a definition.
struct test { test(int i = 0) { } // test(test const&) implicitly declared here }; struct test2 { }; // implicitly declared: test2(), test2(test2 const&) int main() { test t; test copy(t); // causes *definition* of the implicitly // declared copy constructor test2 t2; // causes *definition* of test2::test2() test2 copy2(t2); // causes *definition* of test2::test2(test2 const&) }
默认构造函数是可以不带参数调用的构造函数。它要么不接受任何参数,要么为所采用的每个参数提供默认值。
隐式构造函数是一个术语,通常用于谈论语言中的两个不同概念,
隐式声明的构造函数,它是一个默认或复制构造函数,如果没有提供用户定义的构造函数(默认)或没有提供复制构造函数(复制),将为所有用户类声明。也就是说,一个没有用户声明构造函数的类有一个隐式声明的默认构造函数。
隐式定义的构造函数是使用的隐式声明的构造函数(语言中的odr-used 1并且编译器将为其提供定义。
struct test { test(int i = 0) { } // test(test const&) implicitly declared here }; struct test2 { }; // implicitly declared: test2(), test2(test2 const&) int main() { test t; test copy(t); // causes *definition* of the implicitly // declared copy constructor test2 t2; // causes *definition* of test2::test2() test2 copy2(t2); // causes *definition* of test2::test2(test2 const&) }
In simple terms, a constructor is defaultif it can be called with no arguments. A constructor is implicit(ly declared/defined)if it is not provided by the user but declared/defined.
简单来说,如果可以不带参数调用构造函数,则它是默认构造函数。如果构造函数不是由用户提供而是声明/定义的,则它是隐式的(仅声明/定义的)。
As of the specific cases:
从具体案例来看:
Test t1;
Uses the default constructor, Test(int = 0)
, which is not implicit.
使用Test(int = 0)
非隐式的默认构造函数。
Test t2();
This is a strange quirk of the language, it declares a function that takes no arguments and returns a Test
object.
这是该语言的一个奇怪的怪癖,它声明了一个不带参数并返回一个Test
对象的函数。
Test t3 = 3;
This is called copy-initializationand is equivalent to the composition of an implicit*conversion from 3
to Test
and copy construction of t3
from the result of the conversion. This will use the Test(int)
constructor for the conversion, and then the implicitly defined(and declared) copy constructor. Note: the compiler can optimize away the copy, but it must verify that the copy constructor is available (access specifiers) and can be defined.
这称为复制初始化,等效于隐式*从3
to转换Test
和t3
from 转换结果的复制构造的组合。这将使用Test(int)
构造函数进行转换,然后是隐式定义(和声明)的复制构造函数。注意:编译器可以优化掉副本,但它必须验证复制构造函数是否可用(访问说明符)并且可以被定义。
Test t4(4);
Uses the Test(int)
constructor, which in this case is not acting as a defaultconstructor.
使用Test(int)
构造函数,在这种情况下它不充当默认构造函数。
Test t5 = Test(5);
Equivalent to the Test t3 = 3
case, with the only difference that the conversion from 5
to Test
is explicit in this case. In this example it won't matter, but if the constructor had been marked as explicit
this line would compile while the t3
case would fail.
等效于这种Test t3 = 3
情况,唯一的区别是在这种情况下从5
to的转换Test
是显式的。在这个例子中,这无关紧要,但如果构造函数被标记为explicit
这一行,则该行将编译,而t3
案例将失败。
*) Yet another use of implicit, in this case referring to the fact that the conversion from 3
to Test
is not explicitly requested in the code. Compare this with t5
where the conversion is explicitly requested by the programmer: Test(5)
.
*)隐式的另一种用法,在这种情况下是指代码中没有明确请求从3
到转换的事实Test
。将此与t5
程序员显式请求转换的位置进行比较:Test(5)
。
回答by Luchian Grigore
You seem to be confusing some of the terms. A defaultconstructor is one which takes no parameters, an implicit callis when you directly call the constructor.
您似乎混淆了某些术语。一个默认的构造函数是一个它没有任何参数,一个隐含的调用是当你直接调用构造函数。
Anyway:
反正:
1) Test t1;
1)测试t1;
Default constructor.
默认构造函数。
2) Test t2();
2) 测试 t2();
Function declaration.
函数声明。
3) Test t3 = 3;
3) 测试 t3 = 3;
Copy initialization. Will call the conversion constructor, create a temporary Test
from 3
, and use the copy constructor to create t3
.
复制初始化。将调用转换构造函数,创建一个临时Test
from 3
,并使用复制构造函数创建t3
.
4) Test t4(4);
4)测试t4(4);
Direct initialization. Uses the conversion constructor directly.
直接初始化。直接使用转换构造函数。
5) Test t5 = Test(5);
5) 测试 t5 = 测试(5);
Copy initialization. Similar to 3).
复制初始化。类似于 3)。