3

うーん... を印刷するとsizeof(struct MyStruct)、このコードに対して (2 ではなく) 3 が出力されるのはなぜですか?

#pragma pack(push, 1)
    struct MyStruct
    {
        unsigned char a : 6;
        union
        {
            struct
            {
                unsigned int b : 9;
            };
        };
    };
#pragma pack(pop)

問題が発生した場合に備えて、Windows 7 x64 で MinGW GCC 4.5.0 を実行していますが、正直なところ、結果は奇妙で、コンパイラと OS はここではあまり重要ではないと思います。:\

4

2 に答える 2

13

バイト アラインされていないアドレスからフィールドを開始することはできません。あなたが期待している:

6 bits + 9 bits -> 15 bits -> 2 bytes

しかし、あなたが得ているのは:

6 bits -> 1 byte
9 bits -> 2 bytes
total ->  3 bytes

データは次のように保存されています。

| 1 byte | 2 byte |3 byte | 
 aaaaaaXX bbbbbbbb bXXXXX  

あなたが期待していたとき:

| 1 byte | 2 byte |
 aaaaaabb bbbbbbbX  

編集:以下のコメントに基づいて明確にするために:

共用体 (およびそれを含む構造体) は、バイト境界で整列されている必要があります。内容が 9 ビットだけであることは問題ではありません。共用体/構造体自体は完全な 16 ビットです。次のことはできないことに注意してください。

struct MyStruct
{
    unsigned char a : 6;
    union
    {
        struct
        {
            unsigned int b : 9;
        } c:9;
    } d:9;
};

C では構造体全体のビットサイズを指定できないためです。

于 2011-02-20T03:59:02.527 に答える
0

@nssによって与えられた答えに加えて-私の謝罪、コメントがフォーマットにそれほど制限されていなければ、これはコメントだったでしょう:

#include <stdlib.h>

struct Test {
  unsigned short x : 6;
  unsigned short y : 1;
  unsigned short z;
};

int main( int argc, char *argv[] ) {
  printf( "sizeof( Test ) = %d\n", sizeof( struct Test ) );

  return 0;
}

サイズは「4」と表示されます。gcc、g ++、およびSunStudioのCCとccでテストしました。

私はあなたがやろうとしていることをすることをお勧めしませんが、おそらくあなたは組合で​​やろうとしていることをすることができます。私は次のようなコードを見ました(しかし自分で書いたわけではありません):

struct Test {
  unsigned short x1 : 6;
  unsigned short x2 : 3;
                    : 1; // unused
  unsigned short x3 : 4;
  // ...
};

構文が少し間違っているかもしれません...しかし、私はそうは思いません。

要点:目的のレイアウトで2つの別々の構造体(または構造体とユニオン)を作成し、それらが重なる場所にダミーメンバーを挿入し、それらを結合します。

于 2011-08-26T18:33:08.450 に答える