厳密なエイリアシングルールによると:
struct B { virtual ~B() {} };
struct D : public B { };
D d;
char *c = reinterpret_cast<char*>(&d);
異なるタイプのオブジェクトへのAchar*
は有効です。しかし、今の問題は、&dの同じアドレスを指しているのでしょうか?同じアドレスを返すというC++標準による保証は何ですか?
厳密なエイリアシングルールによると:
struct B { virtual ~B() {} };
struct D : public B { };
D d;
char *c = reinterpret_cast<char*>(&d);
異なるタイプのオブジェクトへのAchar*
は有効です。しかし、今の問題は、&dの同じアドレスを指しているのでしょうか?同じアドレスを返すというC++標準による保証は何ですか?
c
実際に同じ値を&d
持っています。再解釈キャストc
して aD*
に戻すと、逆参照できる有効なポインターが得られます。c
さらに、不透明な配列 (の最初の要素へのポインター) として扱うことができます。char[sizeof(D)]
これは、ポインターを char ポインターにキャストする主な目的ですofile.write(c, sizeof(D));
。プリミティブ型 (およびその配列)。複合型のバイナリ レイアウトは、一般に移植可能な方法で指定されていないためです。
@Oli が正しく指摘しているように、私に補強してもらいたいのですが、複合型全体をシリアライズするべきではありません。ポリモーフィック クラスの実装とデータ フィールド間のパディングが指定されておらず、アクセスできないため、結果がデシリアライズ可能になることはほとんどありません。
同様の理由によりreinterpret_cast<char*>(static_cast<B*>(&d))
、不透明な配列として扱われる可能性があることに注意してください。char[sizeof(B)]
セクション 5.2.10、2003 C++ 標準のポイント 7 は次のように述べています。
オブジェクトへのポインターは、異なる型のオブジェクトへのポインターに明示的に変換できます。ただし、「T1 へのポインター」型の右辺値を「T2 へのポインター」型 (ここで、T1 と T2 はオブジェクト型であり、T2 のアラインメント要件は T1 のアラインメント要件よりも厳密ではありません) に変換し、元の型に戻します。元のポインター値、そのようなポインター変換の結果は指定されていません。
「同じアドレス」が「元のポインタ値」を意味する場合、このエントリは「はい」と表示されます。
意図は明らかです (議論する必要があるものではありません)。
reinterpret_cast
ターゲット型がすべてのアドレス値を表すことができない場合を除き、 address の値を変更することはありません (小さな整数型のように、組み込みアライメントを持つポインター型: f.ex. 偶数アドレスのみを表すことができるポインター、またはオブジェクトへのポインター)関数へのポインターは混在できません...)。
標準の文言はそれを捉えることができませんが、それは実際に実際の問題があることを意味するものではありません。
char *c = reinterpret_cast<char*>(&d);
c
常にの最初のバイトを指しd
ます。