当我从函数返回自动变量时,为什么复制构造函数不起作用?

问题描述

在下面的示例中,我想找出为什么当我从doit()函数返回自动变量时未调用复制构造函数的原因。我知道之所以会调用处理程序的第一个版本,是因为我们有一个临时对象,但无法弄清为什么在创建该临时对象(将所有内容从s复制到临时对象)时不调用复制构造函数。

#include <iostream>
using namespace std;


class S{
    public:
        S(){std::cout<<"Constructor\n";}
        S(const S& s){std::cout<<"Copy Constructor\n";}
        ~S(){std::cout<<"Destructor\n";}
};

S doit(){
    S s;
    return s; 
}

void handler(S&& r){
    std::cout<<"Here\n";
}
void handler(const S& r){
    std::cout<<"Here2\n";
}

int main() {
    handler(doit());
}

解决方法

实际上,根据语言规则,在您的代码中有一个构造函数被调用。但是,编译器对此进行了优化,因此您看不到该调用。如果您使用-fno-elide-constructors进行编译,则应该看到正在调用复制构造函数。

请注意,只会删除复制构造函数,因为默认的move-constructor被取消了。如果您这样添加回去:

S(S&&) = default;

然后将调用此move-constructor。这是demo

相关问答

错误1:Request method ‘DELETE‘ not supported 错误还原:...
错误1:启动docker镜像时报错:Error response from daemon:...
错误1:private field ‘xxx‘ is never assigned 按Alt...
报错如下,通过源不能下载,最后警告pip需升级版本 Requirem...