仕事でC言語のコードを見ていて、シフト演算に関するバグにはまったので備忘録として挙げておきたいと思います。
#include <stdio.h> int main(int argc, char **argv) { char num = 0xB3; // - 77 unsigned short hoge = (num << 0); printf("0x%02X", hoge); return 0; }
のようなコードを書いた場合hogeには何が入るでしょうか。
ここではchar型の変数を0bitシフトして、unsigned short型の変数に代入しています。
恐らくhogeは0x00B3になると思われたのではないでしょうか。というより私はそう思いました。
残念ながら答えは
「分からない」
が正解です。
私の手元のGCCでは、hogeには0xFFB3が入りました。
ちなみに unsigned char num = 0xB3;
とした場合には、hogeは0x00B3になります。
シフト演算による上位ビットに何が入るかはC言語の仕様では定義されておらず、処理系依存になっているそうです。この挙動は知りませんでした。
ビット演算やシフト演算を扱う際は無意識に符号無し型(unsigned)を使っていたのでこれまで遭遇しなかったんだと思います。