zoukankan      html  css  js  c++  java
  • 位运算基础

    基础内容简介
         在做转换之前先要明确几个简单的概念。首先本文是以java为语言,以int为例子。 long数据类型在原理上是一致的。

         1  int 在java中是32位, byte是8位。

         2  原码,反码,补码简介

             原码:就是二进制码,最高位为符号位,0表示正数,1表示负数,剩余部分表示真值。

             反码:在原码的基础上,正数反码就是他本身,负数除符号位之外全部按位取反。

             补码:正数的补码就是自己本身, 负数的补码是在自身反码的基础上加1.

         3  看到这里又涉及到了一个按位与的操作, 所以我们要理解&(与), | (或), ^ (异或),~ (按位取反)

             & :当2个都为1的时候为1, 其他都是0 。 1&1 = 1, 1&0 = 0, 0&0 = 0; 他的作用是清0

             | : 当2个只要有一个为1,就是1. 1|0 = 1; 0|0 = 0,  1|1 = 1;

             ^: 相同为0, 不相同为1, 1^0 = 1, 1^1 = 0,  0^0 = 0; 他的作用是定位翻转。

             ~: 按位取反,0变为1, 1变为0;

          之所以要明确原码,反码,补码,是因为java中变量都是以补码的形式保存的。

          比如 整行30 他的原码是:0001 1110. 正数,所以反码,补码都是0001 1110. 

          对于负数:-7 ,他的原码是 1000 0111, 第一位1表示是此数是负数。他的反码是:1111 1000, 补码在反码的基础上加1, 所以它的补码是1111 1001, 所以他的二进制数就是1111 1001. 对于负数根据二进制求真值,就是再补码的基础上再求补码。 而之所以引入补码的原因是因为: 1 如果用源码,那么0000 0000 和1000 0000 貌似都0, +0 , 和- 0. 所以这造成了问题,第二个原因是因为cpu计算器只有加法没有减法, 减法需要用正数和负数相加得到。

    如“-16+11”的运算:

    11110000     + -16的补码

    00001011       11的补码

    ————

    11111011       - 5的补码

        4  因为byte是8位,int是32位所以在转换过程中,肯定涉及到了移位, 在java中<<  (左移), >>(带符号右移), >>>(无符号右移)

    << 左移,比如,  a << b, a表示需要移位的整行, b表示向左移动的位数, 左移的规则是,右端(低位)补0, 丢去高位

    比如 0000 0000 0000 0110, 左移2位就是0000 0000 0001 1000. 如果移动的位数大于32, 那么就需要取余, 比如移动34位,那么实际应该是 : 34%32 = 2, 左移2位。左移在不溢出的情况下移动一位就相当于乘2。

    >>右移,比如 , a >>b, a表示需要变换的数值, b表示移动的位数,右移的一点要明确,符号位不变,左端(高位)补充的是符号位,比如 0000 0000 0000 1011, 右移2位是 1100 0000 0000 0010. 负数的移位高位补充的是1, 因为这个,所以变换的时候需要&0xFF.

    >>>无符号右移,顾名思义是指移动的时候不考虑符号,右移的时候高位补0.

    代码
    明确了以上概念,写代码反而简单了:

    /**
    * int到byte[] 由高位到低位
    * @param i 需要转换为byte数组的整行值。
    * @return byte数组
    */
    public static byte[] intToByteArray(int i) {
    byte[] result = new byte[4];
    result[0] = (byte)((i >> 24) & 0xFF);
    result[1] = (byte)((i >> 16) & 0xFF);
    result[2] = (byte)((i >> 8) & 0xFF);
    result[3] = (byte)(i & 0xFF);
    return result;
    }

    /**
    * byte[]转int
    * @param bytes 需要转换成int的数组
    * @return int值
    */
    public static int byteArrayToInt(byte[] bytes) {
    int value=0;
    for(int i = 0; i < 4; i++) {
    int shift= (3-i) * 8;
    value +=(bytes[i] & 0xFF) << shift;
    }
    return value;
    }
     

     
    ————————————————
    版权声明:本文为CSDN博主「雨打瓦」的原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接及本声明。
    原文链接:https://blog.csdn.net/alvinhuai/java/article/details/82790888

  • 相关阅读:
    Ubuntu 18.04.2 LTS美化方案
    Ubuntu 16.04升级18.04
    Spark性能优化指南——高级篇
    Spark性能优化指南——基础篇
    遗传算法(Genetic Algorithm)——基于Java实现
    Linux sar命令参数详解
    Gdb调试多进程程序
    P8.打印整数
    Algorithm Book Index
    Debugging with GDB (8) 4.10 Debugging Programs with Multiple Threads
  • 原文地址:https://www.cnblogs.com/sidesky/p/12726350.html
Copyright © 2011-2022 走看看