C++ g++;不';如果复制构造函数是模板化的,是否调用它?
tl;dr:如果复制构造函数前面有C++ g++;不';如果复制构造函数是模板化的,是否调用它?,c++,templates,C++,Templates,tl;dr:如果复制构造函数前面有template,并且构造函数签名中使用了Something,则不会调用该构造函数 概念证明(): 注意复制构造函数中的是如何不打印的 使复制构造函数非模板化(即删除签名中的模板并将相关更改为T)可以解决我的问题 $ g++ --version g++ (GCC) 6.2.1 20160830 编译和执行命令: g++ -Wall -Wextra -pedantic -std=c++11 -O2 -Wshadow -Wformat=2 -Wfloat-equ
template
,并且构造函数签名中使用了Something
,则不会调用该构造函数
概念证明(): 注意复制构造函数中的
是如何不打印的
使复制构造函数非模板化(即删除签名中的模板
并将相关
更改为T
)可以解决我的问题
$ g++ --version
g++ (GCC) 6.2.1 20160830
编译和执行命令:
g++ -Wall -Wextra -pedantic -std=c++11 -O2 -Wshadow -Wformat=2 -Wfloat-equal -Wconversion -Wlogical-op -Wcast-qual -Wcast-align -D_GLIBCXX_DEBUG -D_GLIBCXX_DEBUG_PEDANTIC -D_FORTIFY_SOURCE=2 -fsanitize=address -fsanitize=undefined -fno-sanitize-recover -fstack-protector "test.cpp" -o "test" && "test"
这是怎么回事?函数模板永远不能是复制构造函数,即使实例化的类型显然会使其与复制构造函数的预期签名相匹配。参见[class.copy/2]:
如果类X的非模板构造函数的第一个参数类型为X&、const X&、volatile X&或const volatile X&,并且没有其他参数,或者所有其他参数都有默认参数,则该类X的非模板构造函数是复制构造函数
如果没有用户声明的复制构造函数(有时可能定义为已删除),则所有类都有一个隐式生成的复制构造函数,并带有签名:
Test(Test const &) = default;
当您编写测试t2(t1)时代码>,重载解析选择复制构造函数而不是模板函数,因为在所有其他条件相同的情况下,非模板比模板更可取
请注意,如果您将模板函数更改为Test(Test&t)
,那么现在将通过复制构造函数选择它:“所有其他事物”不再相等,与添加const
以匹配复制构造函数的转换相比,最好实例化模板以精确匹配Test
。引用
类T的复制构造函数是一个非模板构造函数,其第一个参数是T&
,const T&
,volatile T&
或const volatile T&
,或者没有其他参数,或者其余参数都有默认值
因此,构造函数既不能作为模板,也不能具有正确的参数类型
g++ -Wall -Wextra -pedantic -std=c++11 -O2 -Wshadow -Wformat=2 -Wfloat-equal -Wconversion -Wlogical-op -Wcast-qual -Wcast-align -D_GLIBCXX_DEBUG -D_GLIBCXX_DEBUG_PEDANTIC -D_FORTIFY_SOURCE=2 -fsanitize=address -fsanitize=undefined -fno-sanitize-recover -fstack-protector "test.cpp" -o "test" && "test"
Test(Test const &) = default;