c++ - 什么时候返回右值引用会导致未定义的行为?

标签 c++ c++11 undefined-behavior rvalue-reference

在 Stack Overflow 的回答中 here , Kerrek 发布了以下代码。

Foo && g()
{
    Foo y;
    // return y;         // error: cannot bind ‘Foo’ lvalue to ‘Foo&&’
    return std::move(y); // OK type-wise (but undefined behaviour, thanks @GMNG)
}

GManNickG 指出这会导致未定义的行为。

Kerrek 添加

True; you don't really return && from anything but forward and move. It's a contrived example.

让我感到困惑的是,C++11 标准使用返回右值引用的函数调用作为作为 xvalue 的表达式的示例。

An xvalue (an “eXpiring” value) also refers to an object, usually near the end of its lifetime (so that its resources may be moved, for example). An xvalue is the result of certain kinds of expressions involving rvalue references (8.3.2). [ Example: The result of calling a function whose return type is an rvalue reference is an xvalue. —end example ]

那么究竟什么时候返回一个右值引用会导致未定义的行为呢?除了 std::movestd::forward 之外,它是否总是导致未定义的行为?标准是否简洁?或者您是否必须访问未定义行为的返回值才能产生结果?

*“何时”是指“在什么情况下”。我意识到这里没有有意义的时间概念。

最佳答案

转换为引用不会延长局部变量的生命周期。

因此,在本地过期后使用对本地的引用是未定义的行为。

由于本地在函数完成时过期,因此无法使用返回值。

std::movestd::forward 接受一个引用,并返回一个可能不同类型的引用。既没有延长他们争论的生命周期,也没有返回对他们自己 body 局部变量的引用。

这里的 UB 不是返回右值引用,而是基于对象生命周期。它在使用时发生,而不是在转换或返回时发生。

也就是说,返回右值引用几乎不是一个好主意:而是返回一个拷贝。拷贝可以参与生命延长。异常(exception)情况是当您编写类似 forward_as_tuple 的内容时。

关于c++ - 什么时候返回右值引用会导致未定义的行为?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/26321248/

相关文章:

c++ - 带有仿函数修改对象的 const 函数

c++ - "Distributive"可变模板

c++ - 此 C++ 代码是否会产生未定义的行为?

c++ - 是否可以用 C++ 创建网页?

c++ - boost::accumulator::tag::mean 的返回类型

c++ - 可以使用模板在 C++ 中按名称访问位字段成员吗?

c++ - 通过指针运算访问结构体数据成员

rust - 为什么通过指向移动变量的指针写入在 Rust 中没有被确定为 UB?

c++ - 难以得到否定的答案

c++ - 面试位: Giving run time error on submit but correct output on custom test case