gpt4 book ai didi

c++ - 修改临时对象

转载 作者:塔克拉玛干 更新时间:2023-11-03 01:38:25 24 4
gpt4 key购买 nike

有人能说出为什么 test(2) 对象在 test_method() 调用后被销毁吗?

#include<iostream>
#include<string>

using namespace std;

class test
{
int n;

public:
test(int n) : n(n)
{
cout << "test: " << n << endl;
}

~test()
{
cout << "~test: " << n << endl;
}

test & test_method()
{
cout << "test_method: " << n << endl;
return *this;
}
};

int main(int argc, const char *argv[])
{
cout << "main start" << endl;
const test &test1 = test(1);
const test &test2 = test(2).test_method();
cout << "main end" << endl;
}

输出是:

main start
test: 1
test: 2
test_method: 2

~test: 2
main end
~test: 1

最佳答案

test(2).test_method() 返回一个引用,它绑定(bind)到test2,然后它引用的对象在结束时销毁完整的表达,因为它是一个临时对象。 应该不足为奇。

真正令人惊讶的是 test1 仍然是一个有效的引用,因为它直接绑定(bind)到一个临时文件,并且将一个临时文件绑定(bind)到一个引用延长了临时文件的生命周期到引用变量。

您只需要注意,在 test(2) 情况下,临时对象没有绑定(bind)到任何东西。它只是用来调用一些成员函数,然后它的工作就完成了。它不会“照顾”成员函数,或者换句话说,生命周期延长不会通过所有可能的 future 引用传递。


这里有一个简单的思想实验,为什么实际上不可能有“任意生命周期延长”:

extern T & get_ref(T &);

{
T const & x = get_ref(T());

// stuff

// Is x still valid?
}

我们不知道 x 是否在第一行之后仍然有效。 get_ref 可以做任何事情。如果它被实现为 T & get_ref(T & x) { return x; ,我们可能希望有魔法,但也可能是这样的:

namespace { T global; }
T & get_ref(T & unused) { return global; }

不可能在原始翻译单元内决定是否需要扩展任何内容。所以标准目前的方式是,它是一个完全微不足道的局部决定,只是在查看引用声明表达式时做出的,所讨论的临时对象的生命周期应该是多少。

关于c++ - 修改临时对象,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10830883/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com