为什么 std::string a;标准::字符串 b;a + b = “abc”;好吗? [复制]

Why std::string a; std::string b; a + b = "abc"; OK? [duplicate]

提问人:jay_zj 提问时间:10/25/2023 最后编辑:Vlad from Moscowjay_zj 更新时间:10/25/2023 访问量:148

问:

#include <iostream>
#include <string>

int main()
{
    std::string a;
    std::string b;
    a + b = "dadas";
}

PS D:\WeCode\local_c++> & 'c:\Users\z00841303.vscode\extensions\ms-vscode.cpptools-1.5.1\debugAdapters\bin\WindowsDebugLauncher.exe' '--stdin=Microsoft-MIEngine-In-1vidcjmy.adn' '--stdout=Microsoft-MIEngine-Out-ur4nmbvf.4bj' '--stderr=Microsoft-MIEngine-Error-kdush30f.pk5' '--pid=Microsoft-MIEngine-pid-5hgspuj4.obh' '--dbgExe=D:\Program Files\mingw\MinGW\bin\gdb.exe' '--interpreter=mi'

a+b 是右值表达式。为什么可以以这种方式分配值?

C++ 字符串 运算符重载 复制赋值

评论

4赞 TrentP 10/25/2023
类类型对赋值中的右值的限制与基元类型不同。请参阅 stackoverflow.com/questions/34835686/...
2赞 Fareanor 10/25/2023
@kiner_shah 括号是多余的,运算符+的优先级高于赋值运算符。
0赞 Swift - Friday Pie 10/25/2023
@Fareanor实际上,类类型括号可能具有某种含义。这是一种表达方式。因此,老式的“总是写”不仅是错误的,而且是错误的根源。return (expression);
2赞 463035818_is_not_an_ai 10/25/2023
从 C++11 开始,您甚至可以拥有单独的 r 和 lvalue 重载。 可能会出错,但事实并非如此。有关示例,请参阅此处:godbolt.org/z/1ahj4K756std::string::operator=a + b = "dadas";
1赞 463035818_is_not_an_ai 10/25/2023
副本是关于自定义类型的,但如果你看一下重载,你可以看到答案也适用 en.cppreference.com/w/cpp/string/basic_string/operator%3Doperator=std::string

答:

1赞 Vlad from Moscow 10/25/2023 #1

似乎其中一个可能的原因是在 C++ 标准中定义类模板之后,在 C++ 标准中引入了函数的引用说明符。否则,赋值运算符可以声明为,例如std::basic_string

std::basic_string & operator( const std::basic_string & ) &;

下面是一个演示程序,演示如何抑制对右值的赋值。

#include <iostream>

int main()
{
    struct A
    {
        A( int x = 0 ) : x( x ) {}

        A &operator =( const A &a ) &
        {
            x = a.x;

            return *this;
        }

        static A f( const A &a )
        {
            return a;
        }
        int x;
    };

    A a1( 10 );
    std::cout << ( a1 = A::f( A( 20 ) ) ).x << '\n';
    // A::f( A( 20 ) ) = a1; <=== compiler error!
}

另一个原因是允许链接定义为用户定义类型函数的操作。

评论

0赞 Swift - Friday Pie 10/25/2023
嗯,至少与 GCC 实现相匹配,OP 问题是 Microsoft 特有的 afaik,他们总是在那里有很多功能(比如 VS2010 中的 lambda 和类似 Basic 的范围 for 循环而不是 C++ 循环)