- ベストアンサー
C言語の条件式での~(チルド)について
C言語に関しての質問です。 以下のようなプログラムでは変数bをキャストした場合と しない場合で条件式の判定結果が違います。 変数bはもともとunsiged char型なのでキャストは不要だと 思ったのですが、なぜ結果が違うのでしょうか? (条件式if(a != ~b)の判定結果も偽になることを期待していました。) unsigned char a; unsigned char b; a = ~0x98; b = 0x98; if(a != ~b) { printf("こっちは入る"); } if(a != (unsigned char)(~b)) { printf("こっちは入らない"); }
- みんなの回答 (6)
- 専門家の回答
質問者が選んだベストアンサー
C言語とのことなので、C++で検証しても、参考にはなっても結論にはたどりつけませんね。 今回のコードについては処理系によって振る舞いが変わります。 sizeof(char) < sizeof(int) の処理系であれば、unsigned char型のbに~演算子を適用する前に整数拡張が起こり、結果としてint型になります。 sizeof(char) == sizeof(int) の処理系であれば、整数拡張の結果 unsigned int型になりますが、unsigned charとunsigned intの表現範囲が同じなので、キャストしてもしなくても結果は同じになるはずです。
その他の回答 (5)
- tadys
- ベストアンサー率40% (856/2135)
>sizeof(char) == sizeof(int) の処理系であれば > こういう処理系は、あるのでしょうか? 使ったことがあります。 テキサスインスツルメンツのDSP用のCでは char が16ビットです。 sizof(char)もsizeof(int)も値は1でした。 sizof(char)が1なのは規格で決まっているからですね。 PIC用の CCS-Cでは intは8ビットです。
- lailai2580
- ベストアンサー率64% (16/25)
No.2の方のお話を参考にどういう動きが起こってるのか書いてみました。 int型を4バイトとして考えます。 unsigned char a; unsigned char b; a = ~0x98; b = 0x98; ここでは2進数で考えてみます。 aとbにはそれぞれ a ← 01100111 b ← 10011000 が格納されます。 if(a != ~b) この式でaとbが整数拡張されるので a ← 00000000 00000000 00000000 01100111 b ← 00000000 00000000 00000000 10011000 更にbはビット反転しますので、 ~b ← 11111111 11111111 11111111 01100111 となり、aと~bが異なるのでif文内の条件式が真となります。 if(a != (unsigned char)(~b)) ここでもaとbに整数拡張が起こり a ← 00000000 00000000 00000000 01100111 b ← 00000000 00000000 00000000 10011000 ~b ← 11111111 11111111 11111111 01100111 ここで~bがunsigned char型にキャストされますので、 上位24ビットがカットされ (unsigned char)(~b) ← 01100111 この状態でaと~bを比較します。 値はaもbも同じになり、if文の条件式が偽となります。 こんな感じで合ってますかね。
- jacta
- ベストアンサー率26% (845/3158)
> こういう処理系は、あるのでしょうか? 実在します。
- asuncion
- ベストアンサー率33% (2127/6289)
>sizeof(char) == sizeof(int) の処理系であれば こういう処理系は、あるのでしょうか?
- LOHA
- ベストアンサー率52% (203/388)
んー、気にしたことありませんでしたがそうなんですね。 検証してみたVC++用適当ソース(gccならtypeof?)。C++だけどそこは気にしない方針で。 ------------------------------------------------------- #include <stdio.h> #include <typeinfo> int main() { unsigned char a, b; a = ~0x98; b = 0x98; printf("%d, %d\n", a, ~b); // 103, -153 printf("%s\n", typeid(~b).name()); // int printf("%d, %d\n", a, unsigned char(~b)); // 103, 103 printf("%s\n", typeid(unsigned char(~b)).name()); // unsigned char } ------------------------------------------------------- つまり~bはint型になる=負値になっているわけですね。 しらなかった。
お礼
わざわざ検証していただきありがとうございますm(_ _)m なるほど~、int型になっていたのですね。 そのような検証方法があることも勉強になりました。