为什么 return-type 'cv' 会被忽略?

Why return-type 'cv' is ignored?

至少在 'Clang' 和 'GCC' 中。这是一个例子:

char *const InString(char *const p) {

    return gets(p);
}

int main()
{
    static char arr[260];

    char * &&str = InString(arr); //compiles without error - what??????
}

你们中的大多数人可能都知道,在 main' 的第二行中,我们将 return 临时值 ('prvalue') 绑定到 'rvalue reference' 从而延长其使用寿命。所以我的问题是这里发生了什么——return 值的 'cv' 真的被忽略了吗? ]?

*需要ISO C++标准认证。

编辑:问题是在 'C++ 11' 之前,您不允许修改 return 值,因为 'rvalues' 没有被引入,也因为类似的东西:

InString(arr) = nullptr;

毫无意义。但是现在您可以延长 'return-value' 生命周期,因此可以对其进行修改:

auto &&refRetVal = InString(arr);

refRetVal = nullptr;

从这里可以看出 'const' return 'cv' 很有用。如果上面 'InString' 的 return 类型是 'constant' 那么对 'nullptr' 的第二次赋值将是非法的。

return 类型中的 cv-qualifier 仅在第一层被忽略,因此 int const foo() 等于 int foo()int const &foo() 不等于 int &foo().

在你的例子中,你的函数 char *const InString() 等同于 char *InString()

以及关于 char *&&str = InString(arr) 的绑定。函数的 return 是右值(临时值),而 str 是右值引用,所以这是意料之中的。当然,temporary的生命周期是延长到reference的范围内。

顺便说一句,你的代码,用 -Wextra 编译后在 CLang++ 中给出:

warning: 'const' type qualifier on return type has no effect [-Wignored-qualifiers]

在 G++ 中:

warning: type qualifiers ignored on function return type [-Wignored-qualifiers]

在考虑@dyp 提到的引述后,即 [expr]/6:

If a prvalue initially has the type “cv T,” where T is a cv-unqualified non-class, non-array type, the type of the expression is adjusted to T prior to any further analysis.

结论很简单:由于表达式 InString(..) 是纯右值,InString(..)(引用的初始值设定项)的类型被简单地调整为 char*,这显然与引用的目标类型兼容(也 char*)。也就是说,你添加的const在判断函数调用表达式的类型的时候只是简单的忽略了(但是是忽略在查看 函数类型 本身时!)。

但是,对于标量纯右值,引用永远不会 直接 绑定到初始化表达式,而是初始化一个临时变量并将引用绑定到它:

int&& i = 4; // Temporary initialized with 4 and bound to i

int const f();
int&& ref = f(); // Initializer expression has type int - same as above