12

sizeof(Foo)GCC 4.6 でコンパイルすると 0 で1であることに気付きましたsizeof(Bar)。何らかの理由で、空の構造体に空の配列を追加すると、サイズが 0 になりました。両方の構造体のサイズは同じでなければならないと考えました。ここで何が起こっているのですか?

struct Foo
{
    char x[];
};

struct Bar {};
4

3 に答える 3

16

どちらstructの宣言も C 標準では許可されていません。n1570 の 6.7.2.1 (8):

struct-declaration-list に名前付きメンバーが直接含まれていない場合、または匿名構造体または匿名共用体を介して含まれていない場合、動作は未定義です。

そして、同じセクションの段落 18:

特殊なケースとして、複数の名前付きメンバーを持つ構造体の最後の要素は、不完全な配列型を持つ場合があります。これは、柔軟な配列メンバーと呼ばれます。ほとんどの場合、柔軟な配列メンバーは無視されます。特に、構造体のサイズは、省略が意味するよりも多くの後続パディングがある場合を除いて、柔軟な配列メンバーが省略されたかのようになります。

(私のものを強調)

柔軟な配列メンバーは C++ では許可されていないため、コードも有効な C++ ではありません。

これは有効なコードではないsizeofため、これらに対して によって報告される値は無意味です。

于 2012-06-10T19:38:04.953 に答える
1

CおよびC++は、ゼロサイズのオブジェクトを許可しません。

gccはそれらを拡張機能としてサポートします。次のような適切なオプションを使用してコンパイルする場合

gcc -std=c99 -pedantic -Wall -Wextra

gccは少なくともそれらについて警告します。g++にも同様のオプションがあります。

于 2012-06-10T20:07:14.883 に答える
1

空のクラスであっても、 sizeof 演算子は決して 0 を返しません。

ここmsdnでわかるよう

さらに、msdn は次のように述べています。

sizeof 演算子は、次のオペランドでは使用できません。

  • 機能。(ただし、sizeof は関数へのポインターに適用できます。)
  • ビット フィールド。
  • 未定義のクラス。
  • タイプボイド。
  • 動的に割り当てられた配列。
  • 外部配列。
  • 不完全な型。
  • 不完全な型の括弧で囲まれた名前。
于 2012-06-10T19:40:02.343 に答える