C++拷贝构造函数:C++ Primer

浏览:27日期:2023-03-22

问题描述

itemStr it_str = '123456';

这样的代码应该是拷贝初始化?如果是拷贝初始化,那么在C++ Primer 中文版第五版中441页提到

拷贝初始化是依靠拷贝构造函数或移动构造函数来往成的

但是实际调用的却是itemStr(const char *s)

这是为什么,是书的错误还是编译器的优化操作

itemStr类,如上所写会输出This is normal constructor2.

class itemStr{public: itemStr() :str() {std::cout << 'This is default constructor.' << std::endl; } itemStr(std::string s) :str(s) {std::cout << 'This is normal constructor1.' << std::endl; } itemStr(const char *s) :str(s) {std::cout << 'This is normal constructor2.' << std::endl; } itemStr(const itemStr &it) :str(it.str) {std::cout << 'This is copy constructor.' << std::endl; } itemStr& operator=(const itemStr &it) {str = it.str;std::cout << 'This is copy-assignment operator constructor.' << std::endl;return *this; }private: std::string str;};

问题解答

回答1:

书上没有错误,这个初始化语法是拷贝初始化。运行时没有调用拷贝/移动构造函数是因为编译器做了copy elision优化。即便在拷贝/移动构造函数有可见的副作用时,编译器依然被允许进行这种优化。结果就是你无法观察到期望的输出。

也就是说itemStr it_str = '123456';是拷贝初始化,它的确需要一个可用的拷贝/移动构造函数。以下代码在gcc/clang下编译会报编译错误。

class A { public: A(const char *) {} A(const A &) = delete; A(A &&) = delete;};int main() { A x = 'abc'; return 0;}

main.cc: In function ‘int main()’:main.cc:12:9: error: use of deleted function ‘A::A(A&&)’ A x = 'abc'; ^main.cc:8:3: note: declared here A(A &&) = delete; ^main.cc:5:3: note: after user-defined conversion: A::A(const char*) A(const char *) {} ^

相关文章: