Golang中的移位指令

The go spec says:

<<    left shift             integer << unsigned integer

What if the left side is type of uint8:

var x uint8 = 128
fmt.Println(x << 8)      // it got 0, why ?
fmt.Println(int(x)<<8)   // it got 32768, sure

Questions:

  1. when x is uint8 type, why no compile error?
  2. why x << 8 got result 0

For C/C++,

unsigned int a = 128;
printf("%d",a << 8); // result is 32768.

Could anyone explain? Thank you.

  1. Because uint8 is an unsigned 8-bit integer type. That's what "u" stands for.

  2. Because uint8(128) << 8 shifts the value, turning 1000 0000 into 0000 0000.

    int(x) makes it 0000 0000 0000 0000 0000 0000 1000 0000 (on 32 bit systems, since int is architecture-dependant) and then the shift comes, making it 0000 0000 0000 0000 1000 0000 0000 0000, or 32768.

The left shift operator is going to shift the binary digits in the number to the left X number of places. This has the effect of adding X number of 0's to the right hand side the number A unit8 only holds 8 bits so when you have 128 your variable has

x =            1000 0000 == 128
x << 8
x=   1000 0000 0000 0000 == 32768

Since uint8 only holds 8 bits we tak the rightmost 8 bits which is

x =            0000 0000 == 0

The reason you get the right number with an int is an int has at least 16 bits worth of storage and most likely has 32 bits on your system. That is enough to store the entire result.