当b为unsigned char时,(b<<2)>>2与b&0x3F的差异及异常问询
无符号字符移位与按位与的结果差异解析
一、C语言里的运算细节
当b是unsigned char类型、值为0x40(十进制64,二进制01000000)时:
int a = b & 0x3F:0x3F对应二进制00111111,按位与操作会把01000000的高两位清零,结果为00000000,所以a等于0,这部分逻辑符合预期。int a = (b<<2) >> 2:核心原因是C语言的整数提升规则:
所有小于int的整数类型(比如unsigned char)在参与运算前,会自动转换为int类型(只要int能容纳该类型的所有值,unsigned char最大值255,int完全可以承载)。
所以b先被转为int类型的64(二进制为32位的00000000 00000000 00000000 01000000),左移2位后得到256(二进制00000000 00000000 00000001 00000000),此时没有溢出,再右移2位就回到了64。
你之前以为左移2位会变成0,是误以为移位操作在8位的unsigned char上进行,但实际上运算时已经升级为32位int,不会丢失高位。
二、Python中的运算逻辑
Python的整数是任意精度的,没有固定位数限制,移位操作不会丢弃任何高位:
64 << 2得到256,再执行>>2自然回到64,全程没有位丢失,结果必然是64。- 如果要模拟C语言中
unsigned char的移位效果,需要手动截断到8位:比如执行((64 << 2) & 0xFF) >> 2,此时64<<2=256与0xFF按位与后变为0,再右移2位结果还是0,和你最初的预期一致。
内容的提问来源于stack exchange,提问作者xinyuan
相关产品推荐
相关产品推荐

