7

int変数のバイト表現をスキャンすると、予期しない結果が得られます。

私が行った場合

int a = 127;
cout << (unsigned int) *((char *)&a);

期待通り127になります。私が行った場合

int a = 256;
cout << (unsigned int) *((char *)&a + 1);

期待通り1になります。しかし、私がそうするなら

int a = 128;
cout << (unsigned int) *((char *)&a);

私は4294967168を持っていますが、それはまあ…かなり派手です。

問題は、値が128であるint変数の最初のバイトを見るときに128を取得する方法はありますか?

4

4 に答える 4

5

同じ理由で(unsigned int)(char)1284294967168:char最も一般的に使用されるシステムではデフォルトで署名されています。128は符号付き8ビット量に収まらないため、にキャストするとchar-128(16進数で0x80)になります。

次に、-128をにキャストすると、 232-128、つまり4294967168が得られますunsigned int

+128を取得したい場合は、のunsigned char代わりにを使用してcharください。

于 2012-11-07T18:35:56.307 に答える
0

charはここで署名されているため、2番目の例では*((char *)&a + 1) = ((char)256 +1) = (0+1) = 1、はとしてエンコードされて0b00000000000000000000000000000001いるため、unsignedintとして1になります。

3番目の例では、は、、つまり2 << 31*((char *)&a) = (char)128 = (char)-127としてエンコードされ、4294967168です。0b10000000000000000000000000000000

于 2012-11-07T18:32:55.220 に答える
0

コメントが指摘しているように、ここで起こっていることは、2の補数の奇妙なことに遭遇しているように見えます。最後のキャストでは、を使用していないunsigned charため、バイトの最上位ビットが正または負の値を示すために使用されています。その場合、値を表すために8ビットのうち7ビットしかないため、正の数の範囲は0〜127になります(全体で-128〜127)。

この範囲を超えると、ラップされ、-128になります。これをキャストバックするunsigned intと、異常に大きな値になります。

于 2012-11-07T18:37:42.527 に答える
0
int a = 128;
cout << (unsigned int) *((unsigned char *)&a);

また、すべてのコードはリトルエンディアンマシンでの実行に依存しています。

おそらくこれらのことを行うべき方法は次のとおりです。

int a = 127;
cout << (unsigned)(unsigned char)(0xFF & a);

int a = 256;
cout << (unsigned)(unsigned char)(0xFF & (a>>8));

int a = 128;
cout << (unsigned)(unsigned char)(0xFF & a);
于 2012-11-07T18:39:48.903 に答える