首页 > 解决方案 > c++ 运算符重载 += 有效,但 << 无效

问题描述

我预计 += 和 << 会起作用,但 << 不知何故不起作用。

这是我的代码:

#include <iostream>

using namespace std;

struct Pos{
    int x;
    int y;

    void operator+=(Pos vel){
        x += vel.x;
        y += vel.y;
    }
};

struct Obj{
    string name;
    Pos pos;

    void info(){
        cout << name << endl;
        cout << pos.x << ", " << pos.y << endl;
        cout << endl;
    }
    void operator<<(Pos vel){
        pos += vel;
    }
    void operator+=(Pos vel){
        pos += vel;
    }
};


int main(){
    Pos p{10, 20};
    Obj car{"Car", p};
    Obj truck{"Big truck", {40, 20}};

    car.info();
    truck.info();

    //doesn't work
    car << {0, 10};
    //works
    car += {5, 10};
    //works
    car << Pos{0, 10};
    //works
    car += Pos{5, 10};

    car.info();
} 

他们中的大多数都有效,但是 car << {0, 10};

表明:

[Error] expected primary-expression before '{' token

我想知道使用构造函数之间有什么区别+=以及<<为什么会起作用。

我在这里想念什么?

标签: c++oopoperator-overloading

解决方案


这:{10, 20}是一个花括号初始化列表。它不是一个表达式。因此,它只能出现在特定的 C++ 语法片段中

例如,braced-init-lists 可以出现在类型名之后,这意味着它们初始化该类型的纯右值。它们可以作为函数的参数出现。并且(在其他几个中)它们可以出现在赋值运算符的右侧。

请注意,这+=是一个赋值运算符。

<<不是这些特定的地方之一。因此,一个赤裸的大括号初始化列表不能出现在<<表达式的任何一侧。<<这与表达式将被转换为调用的事实无关,operator<<因此花括号初始化列表可以被视为函数参数。C++ 语法根本不允许在那里出现花括号初始化列表,因此编译器永远不会走得足够远,甚至无法尝试重载决议来确定要调用哪个函数。


推荐阅读