0
struct A {
  int &r; 
  A (int &i) : r(i) {}
  void foo () const {
    r = 5;  // <--- ok
  }
};

コンパイラは でエラーを生成しませんr = 5;。それはすでにconst-correct
が参照 であることを意味しますか(論理的には) ですか? [関連する質問が 1 つあります。]&rint* const

4

3 に答える 3

5

「すでにconst-correct」とはどういう意味か正確にはわかりませんが、

への代入rは、 のコンストラクターに渡されたものへの代入と同じですAAこれを行うときのインスタンスでは何も変更していないため、 fooconst と宣言されているという事実は障害にはなりません。あなたがこれをしたかのようです:

struct A {
  int * r;
  A (int * i) : r(i) {}
  void foo () const { *r = 5; }
}

const であるという事実は、呼び出されたインスタンスでfoo何も変更しないことを意味します。Aそれと、提供された他のデータを変更することとの間に矛盾はありません。

もちろん、たまたま がrのメンバーへの参照になるように手配した場合A、呼び出しfooによって のインスタンスが最終的に変更されますAconstコンパイラは、メンバー関数の性質が侵害される可能性のあるすべての方法をキャッチすることはできません。メンバー関数を宣言するときはconst、そのような策略に関与しないことを約束しています。

于 2012-04-25T12:36:02.040 に答える
1

私はメンバー関数を、そのような修飾子をまだ持っていないすべてのデータ メンバーのすぐ左にconst暗黙的に挿入すると解釈します。constこれconstは、参照のために暗黙的に既に存在します (int & const r;は不正な構文です)。言い換えれば、参照は命名法を使用するために「すでにconst-correct」です。

constメンバー関数の修飾子が、constすべてのデータ メンバーのすべての可能な有効な位置に挿入する効果を持っていればいいのですが(たとえば、データ メンバーはメンバー関数のint ** foo;ようint const * const * const foo;に動作しconstます)、それは起こることではありません。標準が言うことは起こります。

于 2012-04-25T12:51:48.700 に答える
1

はい、論理的には と同等ですint* const

この場合、値r参照への不要な変更を防ぐために、適切に修飾されたアクセサーを作成して使用することをお勧めします。

于 2012-04-25T12:33:02.647 に答える