一、位操作符
(1)位与&
- 位与符号是一个&,两个&&是逻辑与。
- 位与时两个操作数是按照二进制位彼次对应位相与的,逻辑与是两个操作数作为整体来相与的。(举例:0xAA&0xF0=0xA0, 0xAA && 0xF0=1)
(2)位或|
- 位或符号是一个|,两个||是逻辑或。
- 位或时两个操作数是按照二进制位彼次对应位相与的,逻辑或是两个操作数作为整体来相或的。
(3)位取反~
- C语言中位取反是~,C语言中的逻辑取反是!;
- 按位取反是将操作数的二进制位逐个按位取反,而逻辑取反是真(在C语言中只要不是0的任何数都是真)变成假(在C语言中只有0表示假)、假变成真。
(4)位异或^
(5)左移位<<,右移位>>
- C语言的移位要取决于数据类型。
- 对于无符号数,左移时右侧补0(相当于逻辑移位),右移时左侧补0(相当于逻辑移位)。
- 对于有符号数,左移时右侧补0(叫算术移位,相当于逻辑移位),右移时左侧补符号位(如果正数就补0,负数就补1,叫算术移位)。
- 嵌入式中研究的移位,以及使用的移位都是无符号数。
二、位操作在操作寄存器时的特殊作用
1、寄存器操作的要求:特定位改变而不影响其他位
- ARM是内存与IO统一编址的,ARM中有很多内部外设,SoC中CPU通过向这些内部外设的寄存器写入一些特定的值来操控这个内部外设,进而操控硬件动作。
- 寄存器的特点是按位进行规划和使用,但是寄存器的读写却是整体32位一起进行的(也就是说你只想修改bit5~bit7是不行的,必须整体32bit全部写入)。
- 寄存器操作要求是在设定特定位时不能影响其他位。
- 读-改-写三部曲。当想改变一个寄存器中某些特定位时,先读出寄存器整体原来的值,然后修改特定位,再将修改后的值整体写入寄存器。。
2、特定位清零用&
3、特定位置1用|
4、特定位取反用^
- (任何数,其实就是1或者0)与1位异或会取反,与0位异或无变化。
- 要取反的特定位为1,其他位为0,然后将这个数与原来的数进行位异或即可。
三、使用位操作构建特定的二进制数
- 如果要的这个数比较少位为1,大部分位为0,则可以通过连续很多个1左移n位得到。
- 如果要的数是大部分位为1,则可以通过先构建其位反数,然后再位取反来得到。
- 如果要的数中连续1(连续0)的部分不止1个,那么可以通过多段分别构造,然后再彼此位与即可。
四、使用用宏定义来完成位运算