0

リンク リストのように複数のインスタンスがリンクされているクラスを作成しています。関連するコードのベアボーンの例を次に示します。

class A
{
  public:
    void setNext(const A& node) { next = &node; }
    const A& getNext() const { return *next; }

  private:
    const A* next;
}

は によって変更されていないため、 へsetNextの引数を宣言しました。クラス A も次のノードを変更しないため、メンバー変数が宣言されます。で問題が発生します。現在のノードから次のノードを取得するオブジェクトは、ノードを変更する必要がありますが、メンバー変数は返される参照であるため、同様に変更する必要があります。constnodesetNextnextconstgetNextconstconst

私が読んだことから、const_cast通常は設計が不十分であることを示していますが、次のノードを取得するオブジェクト内で使用するか、クラス A 内で使用して非 const 参照を返す必要があるようです。これは有効な使用const_castですか、それとも私の設計のどこかに欠陥がありますか?

この件に関しては、参照を返すかポインターを返すかについて、どちらかの方法で優先することはありますか? A の有効なインスタンスを確実にsetNext取得するために参照を取得しましたが、戻り値はどちらの方法でも返される可能性があります。

4

2 に答える 2

0

リンクリストのプライベートメンバーは非定数でなければならないと思います。たとえば、リストを横断して各メンバーで特定の関数を呼び出すことができるメソッドを実装したい場合があります。そのため、 const next メンバーに関する設計には多くの制限があります。他に、 setNext で参照を受け取るように注意する必要があります。どうすればリストの終わりを知ることができますか? ポインターを使用すると、次を NULL として設定でき、リストの最後になります。ただし、メンバーを非 const のままにして、const オブジェクトを返す getNext を実装できます。この場合は次のようになります。

class A
{
  public:
    void setNext(A* node) { next = node; }
    A& getNext() const { return *next; }
    const A& getNext() const { return *next; }

  private:
    A* next;
}
于 2013-09-06T17:52:59.570 に答える
0

まず、車輪を再発明しないでください。このような侵入リストをすでに実装している可能性がある場合boost::intrusiveは、追加の作業は必要ありません! std::listまたは別の標準コンテナを使用することさえできるかもしれません。

しかし、あなたしなければならない場合:

  • 次の変数へのポインターは、それが指すノードconstを変更する必要がある可能性があるため、そうではありません。next
  • setNext非 const 項目ポインターを格納できる必要があるため、非 const 参照によってパラメーターを取得する必要があります。
  • getNext:const A& getNext() const { return *next; }との 2 つのオーバーロードを作成します。A& getNext() { return *next; }
于 2013-09-06T17:49:10.020 に答える