gpt4 book ai didi

c++ - 重载运算符返回什么类型的值(对于用户自定义类型): rvalue or lvalue?

转载 作者:搜寻专家 更新时间:2023-10-31 01:24:51 25 4
gpt4 key购买 nike

我正在阅读 Scott Meyers 的《Effective C++: 55 Specific Ways to Improve Your Programs and Designs》,他说:

Having a function return a constant value is generally inappropriate, but sometimes doing so can reduce the incidence of client errors without giving up safety or efficiency. For example, consider the declaration of the operator* function:

class Rational { ... };

const Rational operator*(const Rational& lhs, const Rational& rhs);

根据 Meyers 的说法,这样做可以防止像这样的“暴行”,如果 a、b 是原始类型,这将是非法的:

Rational a, b, c;

...

(a * b) = c;

这让我很困惑,在试图理解为什么上述赋值对于原始类型而不是用户定义类型是非法的时,我遇到了右值和左值

在看了一些SO问题后,我仍然觉得我对右值和左值没有很好的理解,但这是我的基本理解:左值引用内存中的一个位置,因此可以分配给(它可以是在 = 运算符的两侧也是如此);然而,右值不能被分配,因为它不引用内存位置(例如,函数返回和文字的临时值)

我的问题是:为什么分配给两个数字/对象的乘积对于用户定义的类型是合法的(即使它没有意义)而不是基元?它与返回类型有关吗?重载的 * 运算符返回可分配值还是临时值?

最佳答案

[expr.call]/14: A function call is an lvalue if the result type is an lvalue reference type or an rvalue reference to function type, an xvalue if the result type is an rvalue reference to object type, and a prvalue otherwise.

这是有道理的,因为结果没有“名字”。如果您返回一个引用,则意味着它是对某处某个对象的引用,该对象确实“有名称”(通常但并非总是如此)。

然后是这个:

[expr.ass]/1: The assignment operator (=) and the compound assignment operators all group right-to-left. All require a modifiable lvalue as their left operand; their result is an lvalue referring to the left operand.

这是说赋值需要在左侧有一个左值。到目前为止,一切都很好;你自己已经介绍过了。

那么非 const 函数调用结果如何工作?

根据特殊规则!

[over.oper]/8:: [..] Some predefined operators, such as +=, require an operand to be an lvalue when applied to basic types; this is not required by operator functions.

… 和应用于类类型对象的 = 调用运算符函数

我不能轻易回答“为什么”:从表面上看,在处理类时放宽此限制是有道理的,而对内置函数的原始(继承)限制似乎总是有点过分(在我的意见),但出于兼容性原因必须保留。

但是,像 Meyers 这样的人指出,现在返回 const 值以有效地“撤消”此更改变得有用(有点)。

最终,无论哪种方式,我都不会努力寻找强有力的理由。

关于c++ - 重载运算符返回什么类型的值(对于用户自定义类型): rvalue or lvalue?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/57590241/

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