写点什么

秒懂!进制和位运算

用户头像
阿粤Ayue
关注
发布于: 21 小时前
秒懂!进制和位运算

关于进制

进制是计算机中数据的一种表示方法。 N 进制的数可以用 0~(N-1) 的数表示, 超过 9 的用字母 A-F 表示 。


  • 十进制:用 0~9 的数表示 , 逢 10 进 1

  • 二进制:由 0-1 组成

  • 八进制:由 0-7 组成,逢 8 进 1

  • 十六进制: 由 0-9,A-F 组成。0-9 对应 0-9,A-F 对应 10-15。字母不区分大小写

机制的转换

二进制转十进制


二进制数的第 0 位的权值是 2 的 0 次方,第一位是 2 的 1 次方......


所以,设有一个二进制数:101100100,转换为十进制为(从右向左):



八进制转十进制


八进制数的第 0 位的权值是 8 的 0 次方,第一位是 8 的 1 次方......


所以,设有一个八进制数:1507,转换为十进制为(从右向左):



十六进制转十进制


十六进制数的第 0 位的权值是 16 的 0 次方,第一位是 16 的 1 次方......


所以,设有一个十六进制数 2AF5,转换为十进制为(从右向左):


快速的进行 2 进制,10 进制,16 进制的相互转换

二进制的 8421


首先我们来看一个二进制数:1111,它是多少呢?你可能还要这样计算:1×2º+1×2¹+1×2²+1×2³=1×1+1×2+1×4+1×8=15。


我们必须直接记住 1111 每一位的权值,并且是从高位往低位记:8、4、2、1。


即,最高位的权值为 2³=8,然后依次是 2² =4,2¹=2,2º=1。


记住 8 4 2 1,对于任意一个 4 位的二进制数,我们都可以很快算出它对应的 10 进制值。


接下来我们练习 通过 8421 的方式 进行 快速的计算 , 2,10,16 进制的转换


1111 = 8 + 4 + 2 + 1 = 15 =F1110 = 8 + 4 + 2 + 0 = 14= E1101 = 8 + 4 + 0 + 1 = 13= D1100 = 8 + 4 + 0 + 0 = 12 =C1011 = 8 + 0 + 2 + 1 = 11= B1010 = 8 + 0 + 2 + 0 = 10 =A1001 = 8 + 0 + 0 + 1 =9 =9……0001 = 0 + 0 + 0 + 1 = 1= 10000 = 0 + 0 + 0 + 0 = 0= 0
复制代码


  • 二进制数转十六进制

  • 以 4 位一段,分别转换为十六进制,如:


  • 十六进制转二进制

  • 反过来,当我们看到 FD 时,如何迅速将此十六进制转二进制呢?

  • 看到 F,我们需知道它是 15,然后 15 如何用 8421 凑呢?

  • 应该是:8 + 4 + 2 + 1,所以四位全为 1 :1111。

  • 接着转换 D,看到 D,知道它是 13,13 如何用 8421 凑呢?

  • 应该是:8 + 4 + 1,即:1101。

  • 所以,FD 转换为二进制数,为:1111 1101

  • 十进制转二进制

  • 由于十六进制转换成二进制相当直接,所以,我们需要将一个十进制数转换成二进制数时,也可以先转换成十六进制然后再转换成二进制。比如,十进制数 1234 转换成二制数,如果要一直除以 2,直接得到 2 进制数,需要计算较多次数。所以我们可以先除以 16,得到 16 进制数:


  1234÷16=77...2  77÷16=4...13(D)  4÷16=0...4
复制代码


十六进制为:4D2


转二进制对应为:


  0100   4  1101   D  0010   2
复制代码


即十进制 1234 转二进制为:0100 1101 0010


  • 二进制转十进制

  • 同样,如果一个二进制数很长,我们需要将它转换成十进制数时,除了前面学过的方法是,我们还可以先将这个二进制转换成十六进制,然后再转换为 10 进制。如一个 int 类型的二进制数如下:


  0110 1101 1110 0101 1010 1111 0001 1011
复制代码


我们按四位一组转换为十六进制:6 D E 5 A F 1 B


十六进制转化为十进制:



  • 十进制转十六进制

  • 采余数定理分解,例如将 487710 转成十六进制:


  487710÷16=30481...14(E)  30481÷16=1905...1  1905÷16=119...1  119÷16=7...7  7÷16=0...7
复制代码


487710(10) = 7711E(16)

位运算

计算机中的计算都是以二进制来进行运算的,因此相比在代码中直接使用(+、-、*、/)运算符,合理使用位运算符能提高代码的执行效率。


与(&)

4 & 6 = 4


首先我们需要把两个十进制的数转换成二进制


4  0 1 0 06  0 1 1 0----------4  0 1 0 0
复制代码


用途


  • 清零:若想将一个单元清零,只要与一个各位都为 0 的数值相与,结果就为零

  • 判断奇偶:只要根据最末位判断是 0 还是 1 就可以判断,是 0 就是偶数,是 1 就是奇数


  if ((a & 1) == 0) //如果a是偶数  代替  if (a % 2 == 0) 
复制代码

或(|)

4 & 6 = 6


首先我们需要把两个十进制的数转换成二进制


4  0 1 0 06  0 1 1 0----------6  0 1 1 0
复制代码


用途


  • 常用来对一个数据的某些位设置为 1:若要将一个数 X=10101100 的低四位设置为 1,那么令 Y=00001111,X 与 Y 相或的结果就是将 X 的低四位设置为 1(X | Y = 10101111)

非(~)

在 Java 中,所有数据的表示方法都是以补码的形式表示,如果没有特殊说明,Java 中的数据类型默认是 int,int 数据类型是占 4 个字节,1 字节为 8 位,所以 int 为 32 位,32bit。


补码与原码关系:正数补码与原码相同,负数补码是原码减 1 后取反


例如:5原码是:00000000 00000000 00000000 00000101补码是:00000000 00000000 00000000 00000101(计算机内存储)
例如:-5原码:10000000 00000000 00000000 00000101补码:11111111 11111111 11111111 11111011(计算机内存储)
复制代码


注意:二进制中,最高位是符号位 1 表示负数,0 表示正数


了解了原码补码我们来看位非~运算符


例:~4


4  0 1 0 0-----------5  1 0 1 1
复制代码


4 转为二进制是:0100


补码为:00000000 00000000 00000000 00000100


取反为:11111111 11111111 11111111 11111011(这就是~4 在计算机存储的补码)


需要将补码计算出原码然后转化为十进制,高位不变,取反+1


10000000 00000000 00000000 00000101


转为十进制为:-5


所以 ~4 = -5

异或(^)

4 ^ 6 = 6


首先我们需要把两个十进制的数转换成二进制


4  0 1 0 06  0 1 1 0----------2  0 0 1 0
复制代码


相同为 0,不同为 1


用途


  • 交换两个数:一个数和另一个数异或两次得到还是原来的数


  //不使用临时变量交换两个数  void swap ( int a, int b ) {      if ( a != b) {          a = a ^ b;          b = a ^ b;//a与b异或两次了,现在值为a          a = a ^ b;//用原来的a、b表示的话,这句代码的意思是a^b^a      }  }
复制代码

右移(>>)

4>>1 = 2


4 转为二进制是:0100


正数,高位补 0,负数,高位补 1


左移(<<)

4<<1 = 8


4 转为二进制是:0100


正数,高位补 0,负数,高位补 1



负数在非运算中已做说明,这里不在演示。

无符号右移(>>>)

无符号右移(>>>)只对 32 位和 64 位有意义。


在移动位的时候与右移运算符的移动方式一样的,区别只在于补位的时候不管是 0 还是 1,都补 0。

有趣的取模性质

取模 a % (2^n) 等价于 a & (2^n - 1),所以在 map 里的数组个数一定是 2 的乘方数,计算 key 值在哪个元素中的时候,就用位运算来快速定位。


 public static void main(String[] args) {        //取模a % (2^n) 等价于 a & (2^n - 1)        System.out.println("the 345 % 16 is : " + (345 % 16)); //9        System.out.println("the 345 % 16 is : " + (345 & (16 - 1)));//9 }
复制代码


发布于: 21 小时前阅读数: 7
用户头像

阿粤Ayue

关注

微信搜:Javatv 2019.10.16 加入

秘密基地:javatv.net

评论

发布
暂无评论
秒懂!进制和位运算