zoukankan      html  css  js  c++  java
  • 原码、反码、补码与位运算

    目录导引

      一、原码、反码、补码

      二、位运算

    一、原码、反码、补码

      计算机只有加法运算器,计算器中存储、计算数据都是补码,正数和0的原码、反码、补码相同,负数的原码、反码、补码不同。

      原码:符号位+绝对值(0表示正数,1表示负数)

      反码:符号位不变,其余位取反

      补码:反码+1

      1、为什么要用补码存储,以及补码计算?

      因为原码和反码计算会出现+0 和 -0以及计算错误问题,而补码是正确而简单的,符号位也直接参与运算。

      示例:

      int是4字节,1字节是8位,所以一个int值是32位,第一位是符号位,所以int的取值范围是 -2^31 ~ 2^31-1(10000000 00000000 00000000 00000000~01111111 11111111 11111111 11111111,该二进制是补码)

      分别计算 2+(-1)和1+(-1),过程如下:

      2的原码、反码、补码分别是 00000000 00000000 00000010,00000000 00000000 00000010,00000000 00000000 00000010

      1的原码、反码、补码分别是 00000000 00000000 00000001,00000000 00000000 00000001,00000000 00000000 00000001

      -1的原码、反码、补码分别是 10000000 00000000 00000001,11111111 11111111 11111111 11111110,11111111 11111111 11111111 11111111

      2和-1原码相加,结果为:10000000 00000000 00000011(原码),0代表正数,1代表负数,所以值为-3,错误。

      2和-1反码相加,结果为:00000000 00000000 00000000(反码),对应原码的结果为00000000 00000000 00000000(原码),值为0,错误。

      2和-1补码相加,结果为:00000000 00000000 00000001(补码),对应原码的结果为00000000 00000000 00000001(原码),值为1,正确。

      1和-1原码相加,结果为:10000000 00000000 00000010(原码),值为-2,错误。

      1和-1反码相加,结果为:11111111 11111111 11111111 11111111(反码),对应原码的结果为10000000 00000000 00000000(原码),值为-0,不准确。(关于+0和-0的设计,有兴趣可自行百度)

      1和-1补码相加,结果为:00000000 00000000 00000000(补码),对应原码的结果为00000000 00000000 00000000(原码),值为0,正确。

    二、位运算

      位运算符包括: 与(&)、或(|)、非(~)、异或(^)、左移(<<)、右移(>>)、无符号右移(>>>)

      &:二进制位同时为1时,结果为1,否则为0   

       | :位有一个为1时,结果为1,否则为0

      ~:位0变1,1变0

      ^:位不同时,结果为1,否则为0

      <<:位整体向左移动,右边补0

      >>:位整体向右移动,正数左边补0,负数左边补1

      >>>:位整体向右移动,左边补0

      示例:

    public class BitOperationTest {

    public static void main(String[] args) {
    int a = 13, b = 6;
    System.out.println(" a :" + getBinaryStr(a));
    System.out.println(" b :" + getBinaryStr(b));
    System.out.println(" a&b :" + getBinaryStr(a & b));
    System.out.println(" a|b :" + getBinaryStr(a | b));
    System.out.println(" ~a :" + getBinaryStr(~a));
    System.out.println(" a^b :" + getBinaryStr(a ^ b));
    System.out.println(" a<<b :" + getBinaryStr(a << b));
    System.out.println(" a>>b :" + getBinaryStr(a >> (b - 4)));
    System.out.println(" -a :" + getBinaryStr(-a));
    System.out.println(" a>>>b:" + getBinaryStr(a >> (b - 4)));
    System.out.println("-a>>>b:" + getBinaryStr((-a) >> (b - 4)));
    }

    private static String getBinaryStr(int n) {
    StringBuilder str = new StringBuilder(Integer.toBinaryString(n));
    int len = str.length();
    if (len < 32) {
    for (int i = 0; i < 32 - len; i++) {
    str.insert(0, "0");
    }
    }
    return str.substring(0, 8) + " " + str.substring(8, 16) + " " + str.substring(16, 24) + " " + str.substring(24, 32);
    }
    }

    //Result 
       a    :00000000 00000000 00000000 00001101
       b    :00000000 00000000 00000000 00000110
      a&b   :00000000 00000000 00000000 00000100
      a|b   :00000000 00000000 00000000 00001111
       ~a   :11111111 11111111 11111111 11110010
      a^b   :00000000 00000000 00000000 00001011
      a<<2  :00000000 00000000 00000000 00110100
       -a   :11111111 11111111 11111111 11110011
      a>>2  :00000000 00000000 00000000 00000011
    (-a)>>2 :11111111 11111111 11111111 11111100
      a>>>2 :00000000 00000000 00000000 00000011
    (-a)>>>2:00111111 11111111 11111111 11111100

      如有疑问欢迎提出,如有错误欢迎指正。

      转载请注明本文地址:https://www.cnblogs.com/yqxx1116/p/11657307.html

  • 相关阅读:
    < high performance web sites > 阅读小记
    Gimp制作圆角透明图片
    iphone开发小记
    Android开发小记
    双网卡绑定(suse)
    xen虚拟机操作整理
    linux网络相关命令使用
    lua协程并发下载简单测试
    linux使用技巧(shell/vi/screen)
    爬虫之scrapy框架
  • 原文地址:https://www.cnblogs.com/yqxx1116/p/11657307.html
Copyright © 2011-2022 走看看