2

次の名前空間とクラス階層があります。

namespace Ns1 {
    class Outer {
    private:
           class Inner {
           };
           QSet<Inner> set;
    };
}

次に、グローバル関数を宣言する必要があります。

uint qHash(Ns1::Outer::Inner const& el);
bool operator==(Ns1::Outer::Inner const& el1,
                Ns1::Outer::Inner const& el);

したがって、関数はOuterとInnerのフレンドである必要があります。問題と、関数がグローバルスコープにあることを示すには:

friend uint qHash(Ns1::Outer::Inner const& el);
friend operator==(Ns1::Outer::Inner const& el1,
                Ns1::Outer::Inner const& el);

この場合、前方宣言を処理することはできません。解決策はありますか?

4

1 に答える 1

3

編集:

あなたが正しい!言語が処理できないコーナーケースを見つけました(friend船の宣言は以前に宣言された関数または最も内側の名前空間にのみ適用されるため)。残念ながら、これは、コードを少し再構築する必要があることを意味します。これは、実行したいことを正確にその方法で実行できないためです。

Ns1最も簡単なアプローチは、名前空間で2つの関数を定義してから、usingそれらをグローバル名前空間に定義することです。これは、ネストされた名前空間に2つの追加関数があることを除いて、基本的に必要なものとまったく同じ効果があります。

他の一連のオプションには、根本的な問題への対処が含まれます。クラスオブジェクトのパブリックインターフェイスが、友情が必要となるような適切な機能を提供しないのはなぜですか。たとえば、グローバルスコープでオブジェクトを渡すことができるようにすることを目的としているのに、なぜInnerプライベート内にあるのでしょうか。OuterInner

Innerハッシュ関数と比較関数がの内部状態にアクセスする必要があるのはなぜですか?Innerオペレーターが利用する公開比較インターフェースを提供してみませんか?

于 2013-02-27T16:18:30.533 に答える