0

A と B の 2 つのクラスを定義したいと考えています。A には、クラス B オブジェクトであり、クラス内で初期化されるデータ メンバーがあります。A には、この B 型データ メンバーの値を取得するメソッドもあり、このメソッドは B のフレンド メソッドとして宣言されます。これが私のコードです。

class A{
public:
    int getBValue();
private:
    B b=B(1);
};

class B{
public:
    friend int A::getBValue();
    B(int i):value(i){}
private:
    int value;
};

int A::getBValue(){
    return b.value;
}

当然のことながら、クラス A の定義に不明なタイプ B があるため、コンパイルは失敗しました。ソース内の A と B の定義を交換しようとしましたが、結果はさらに悪いものでした。この A と B の間の相互参照の問題を解決する方法はありますか?

4

2 に答える 2

3

これが完全なコードである場合、問題は、コンパイラがBclass をコンパイルしている時点でa が何であるかを認識していないことAです。これを解決する 1 つの方法は、B 自体を持つ代わりに B へのポインターを作成することです。

ああ

#ifndef CLASS_A
#define CLASS_A

class B;

class A{
public:
    int getBValue();
private:
    B *b;
};

#endif

Bh

#ifndef CLASS_B
#define CLASS_B

#include "A.h"

class B{
public:
    friend int A::getBValue();
    B(int i):value(i){}
private:
    int value;
};

#endif

A.cpp

#include "A.h"
#include "B.h"

int A::getBValue(){
    return b->value;
}
于 2013-12-25T12:17:19.303 に答える
0

type の埋め込みメンバーをBへのポインター (または参照) に置き換えるとB、クラスの動作が変わり、 class のオブジェクトをコピーするときに追加の注意が必要になりますA

A定義を逆にすると、 class のメンバー関数を classのフレンドにすることはできません。これは、宣言時に のB型が不完全であるためです。しかし、クラス全体を友達にすることはできます。AfriendA

Aclassの埋め込みメンバーを持つクラスのソリューションは、次のBようになります。

class A;

class B{
public:
    friend class A;
    B(int i):value(i){}
private:
    int value;
};

class A{
public:
    int getBValue();
private:
    B b=B(1);
};

int A::getBValue(){
    return b.value;
}

行われた変更:

  1. Bの前に宣言A。for の前方宣言Aが使用されます。
  2. クラスを A友達にしBました。これは、Aがまだ完全に定義されていない場合でも機能します。

g++ バージョン 4.7.2 でコンパイル (-std=c++11 が必要B b=B(1);)

とにかく、クラスのメンバーがクラスAのプライベートメンバーにアクセスすることBは、ほとんどの場合回避できる(そしてすべき)ことです(あなたの投稿に関するLaszlo Pappのコメントを参照してください)。

于 2013-12-25T20:14:49.720 に答える