I have a struct that represents a 2d column vector. I've overloaded some operators such as * to mean scalar multiplication in the context of an int and + to mean vector addition in the context of another vector.
I also want to overload the << operator so that I can simply pass the object to cout and have the two elements printed. Currently I am overloading it like below;
struct vector2d
{
private:
    float x;
    float y;
public:
    vector2d(float x, float y) : x(x), y(x) {}
    vector2d() : x(0), y(0) {}
    vector2d operator+(const vector2d& other)
    {
        this->x = this->x + other.x;
        this->y = this->y + other.y;
        return *this;
    }
    vector2d operator*(const int& c)
    {
        this->x = this->x*c;
        this->y = this->y*c;
        return *this;
    }
    friend std::ostream& operator<<(std::ostream& out, const vector2d& other)
    {
        out << other.x << " : " << other.y;
        return out;
    }
};
This works fine, but if I remove the friend keyword I get "too many parameters for this operator function". What does this mean and why does the friend keyword fix it?