2012-02-19 17 views
2

私が意味する、私はクラスに固有のクラス内の演算子をオーバーロードすることはできませんなぜこのオペレータ<<がクラス内で動作しますか?

class A { 
     public: 
      ostream &operator<<(ostream &os);// which doesnt work 

     private: 
      friend ostream &operator<<(ostream &os, const A& a); //Works 
      int i; 

}; 

    Definition 
      ostream &operator<<(ostream &os, const A& a) { 
       os<<a.i; 
       return os; 
      } 

のようにクラス内

をオペレータ< <をオーバーロードしようとしていましたか?または私は何かを逃している?または私はそんなやり方で考えることすら馬鹿ですか?お知らせ下さい。

+2

[Operator overloading](http://stackoverflow.com/questions/4421706/operator-overloading)の可能な複製(特に[この回答を参照してください](http://stackoverflow.com/a/4421719/103167)) –

答えて

12

メンバ関数:

ostream &operator<<(ostream &os); 

はなく、あなたが望むような状況のため、作業を行います。

A a; 
a << std::cout; 

つまり、オブジェクトがオペレータの左側にある場合に呼び出されます。

15

問題は、operator<<が最初のパラメータではなく、2番目のパラメータとしてostreamになることです。そうすれば、myObject << std::coutを行うことができますが、直観的ではなく、operator<<が左結合であるため、コールをチェーンできなくなります。

メンバ関数ではなく、演算子をフレンドとして宣言することのもう1つの利点は、自動変換が行われることです。つまり、Aから派生しないがB(A const&)コンストラクタを持つクラスBがある場合は、std::cout << my_b;を実行してAに変換してから印刷することができます。

友人としてoperator<<を定義することは、好きな場合はクラス内で行うことができます。あなたのコードは、引数が行くべき側面を指定するために、なぜ標準が許可されていません

class A { 
    int i; 
    friend std::ostream& operator<<(std::ostream& o, A const& a) { 
     o << a.i; 
     return o; 
    } 
}; 

のように記述されるだろうか?のは、それがなかったふりをし、指定するleft_ofright_ofキーワードを追加してみましょう:私たちはA a; B b; f(a + b);を行う際

struct B; 

struct A { 
    A left_of operator+(B const&) { 
     return *this; 
    } 
}; 

struct B { 
    B right_of operator+(A const&) { 
     return *this; 
    } 
}; 

今どうなりますか?各クラスには、このケースを扱う演算子があります。つまり、私たちは決定できません。とにかく変換​​の可能性のために多くの演算子が友人になるべきであることを見て、このようなことを許さないことは大きな問題ではなく、この種のあいまいさを防止します。 (もちろん、メンバーオペレータと自由なメンバーを定義することもできますが、これは非常に似たような問題を引き起こします)

ちなみに、あなたのfriend operator<<の定義は何も返されません。チェーンアップを台無しにする。

+0

^u ..... .....しかし、最初のものは意味がありません.....すべての演算子の間で一貫性を維持するために、すべてのものが演算子に正しく表示されるため、実行されました。パラメータ? – howtechstuffworks

+2

匿名のdownvoter、自由にコメントしてください。 –

+0

^LOL、誰かがうんざりしているようだ....... – howtechstuffworks

関連する問題