You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

构造函数调用中圆括号与花括号的差异:std::add_rvalue_reference调用报错解析

问题解析:std::add_rvalue_reference<Test>::type()编译失败的原因

问题场景

可正常运行的代码及输出

运行以下代码可正常输出预期结果:

ASM generation compiler returned: 0
Execution build compiler returned: 0
Program returned: 0
same
same
same

对应的C++代码:

#include <iostream>
#include <type_traits>

struct Test {
    Test() {
        std::cout << "Test ctor\n";
    }
    int func() {
        return 1;
    }
};

int main() {
    if (std::is_same_v<decltype(std::add_rvalue_reference<Test>::type{}.func()),int>) {
        std::cout <<"same\n";
    } else {
        std::cout <<"different\n";
    }
    if (std::is_same_v<decltype(Test().func()),int>) {
        std::cout <<"same\n";
    } else {
        std::cout <<"different\n";
    }
    if (std::is_same_v<decltype(std::type_identity<Test>::type().func()),int>) {
        std::cout <<"same\n";
    } else {
        std::cout <<"different\n";
    }
}

替换后的编译错误

若将代码中的std::add_rvalue_reference<Test>::type{}替换为std::add_rvalue_reference<Test>::type(),会触发如下编译错误:

<source>:14:33: error: reference to type 'Test' requires an initializer
    if (std::is_same_v<decltype(std::add_rvalue_reference<Test>::type().func()),int>) {
                                ^
1 error generated.
ASM generation compiler returned: 1
<source>:14:33: error: reference to type 'Test' requires an initializer
    if (std::is_same_v<decltype(std::add_rvalue_reference<Test>::type().func()),int>) {
                                ^
1 error generated.
Execution build compiler returned: 1

原因分析

  • 类型本质差异:std::add_rvalue_reference<Test>::type的实际类型是Test&&(右值引用类型),而std::type_identity<Test>::type就是Test本身。
  • Test()与type()的解析:Test()和std::type_identity<Test>::type()都是值初始化操作,会直接创建一个临时Test对象,因此能正常调用成员函数func()。
  • Test&&()的解析陷阱:std::add_rvalue_reference<Test>::type()等价于Test&&(),这在C++语法中会被解析为声明一个无参数、返回Test&&类型的函数,而非创建临时对象。此时后续的.func()试图访问函数的成员,自然会触发编译错误——函数本身没有func()成员,且编译器会提示引用类型需要初始化,本质是这里的语法被误解为函数声明而非对象构造。
  • Test&&{}的正确初始化:std::add_rvalue_reference<Test>::type{}是列表初始化操作,对于右值引用类型,这种语法会创建一个临时Test对象,并将右值引用绑定到该临时对象上,因此可以正常调用func()。

内容的提问来源于stack exchange,提问作者cpp

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.23 06:05:05