4

このコードを見てください:

#include <stdio.h>
int main(void)
{
short s = -1;

printf("sizeof(short) = %lu\n", sizeof(short));
printf("sizeof(int) = %lu\n", sizeof(int));
printf("sizeof(long) = %lu\n", sizeof(long));
printf("s = %hd\n", s);
printf("s = %d\n", s);
printf("s = %ld\n", s);

return 0;
}  

次のような出力が得られました。

sizeof(short) = 2  
sizeof(int) = 4  
sizeof(long) = 8  
s = -1  
s = -1  
s = 4294967295  

最後の行で、このs = 4294967295質問の代わりに、C では変数がプロモートされたときにその値が一定のままであることを知ったのはなぜですか。s = -1

4

2 に答える 2

6

sに昇格されてintいます。ここでは 4 バイト タイプです。これは 3 つのケースすべてで発生しています。最初の 2 つは、形式指定子が として渡される型のためのものであるため、 anintが期待されるものです。ただし、最後のケースでは、8 バイト型を期待するフォーマット指定子を指定しています。printf()int

これは、未定義の動作を呼び出しています。

あなたの場合、値の上位バイトでゼロを読み取ったように見え、すでに32ビットに符号拡張された値を64ビットに効果的にゼロ拡張します。ただし、これを実行した結果に依存することはできません。一貫して初期化されていないメモリまたはレジスタを読み取っている可能性があります。明日は違うかもしれません。

引数の昇格は、フォーマット文字列に依存しません。指定したフォーマットの正しい引数を渡すことを常に確認する必要があります。したがって、intは に昇格しませんlong。自分で変換する必要があります。

賢いコンパイラは、これについて警告を発するはずです。

于 2013-02-07T13:13:09.853 に答える
1

変数は、呼び出し中に long に昇格しませんprintf("s = %ld\n", s);。ロングにプロモートする正しい方法はprintf("s = %ld\n", (long) s);.

于 2013-02-07T13:13:27.070 に答える