精华内容
下载资源
问答
  • 模二运算基本方法
    万次阅读
    2016-11-19 23:08:51
    模2运算是一种二进制算法,CRC校验技术中的核心部分,因此,我们在分析CRC算法之前,必须掌握模2运算的规则。 与四则运算相同,模2运算也包括模2加、模2减、模2乘、模2除四种二进制运算。而且,模2运算也使用与四则运算相同的运算符,即“+”表示模2加,“-”表示模2减,“×”或“·”表示模2乘,“÷”或“/”表示模2除。与四则运算不同的是模2运算不考虑进位和借位,即模2加法是不带进位的二进制加法运算,模2减法是不带借位的二进制减法运算。这样,两个二进制位相运算时,这两个位的值就能确定运算结果,不受前一次运算的影响,也不对下一次造成影响。

    ①模2加法运算定义为:
    0+0=0        0+1=1        1+0=1        1+1=0
    例如0101+0011=0110,列竖式计算:
       0 1 0 1
    +0 0 1 1
    ──────
       0 1 1 0

    ②模2减法运算定义为:
    0-0=0        0-1=1        1-0=1        1-1=0
    例如0110-0011=0101,列竖式计算:
       0 1 1 0
    -  0 0 1 1
    ──────
       0 1 0 1

    ③模2乘法运算定义为:
    0×0=0        0×1=0        1×0=0        1×1=1
    多位二进制模2乘法类似于普通意义上的多位二进制乘法,不同之处在于后者累加中间结果(或称部分积)时采用带进位的加法,而模2乘法对中间结果的处理方式采用的是模2加法。例如1011×101=100111,列竖式计算:
           1 0 1 1
         ×  1 0 1
        ──────
                1 0 1 1
         0 0 0 0
    +1 0 1 1
    ────────
       1 0 0 1 1 1

    ④模2除法运算定义为:
    0÷1=0        1÷1=1
    多位二进制模2除法也类似于普通意义上的多位二进制除法,但是在如何确定商的问题上两者采用不同的规则。后者按带借位的二进制减法,根 据余数减除数够减与否确定商1还是商0,若够减则商1,否则商0。多位模2除法采用模2减法,不带借位的二进制减法,因此考虑余数够减除数与否是没有意义 的。实际上,在CRC运算中,总能保证除数的首位为1,则模2除法运算的商是由余数首位与除数首位的模2除法运算结果确定。因为除数首位总是1,按照模2 除法运算法则,那么余数首位是1就商1,是0就商0。例如1100100÷1011=1110……110,列竖式计算:
                   1 1 1 0
           ────────
    1 0 1 1〕1 1 0 0 1 0 0
          1 0 1 1
          ──────
               1 1 1 1
            - 1 0 1 1
           ──────
                 1 0 0 0
              - 1 0 1 1
             ──────
                   0 1 1 0
                - 0 0 0 0
               ──────
                     1 1 0

    更多相关内容
  • 04-C语言进制和位运算

    2021-05-19 12:10:18
    进制是一种计数的方式,数值的表示形式常见的进制十进制、二进制、八进制、十六进制进制书写的格式和规律十进制 0、1、2、3、4、5、6、7、8、9 逢十进一二进制 0、1 逢二进一在C语言中, 如果想用二进制表示某个数, ...

    进制基本概念

    什么是进制?

    进制是一种计数的方式,数值的表示形式

    常见的进制

    十进制、二进制、八进制、十六进制

    进制书写的格式和规律

    十进制 0、1、2、3、4、5、6、7、8、9 逢十进一

    二进制 0、1 逢二进一

    在C语言中, 如果想用二进制表示某个数, 前面需要加上0b;

    八进制 0、1、2、3、4、5、6、7 逢八进一

    在C语言中, 如果想用八进制表示某个数, 前面需要加上0;

    十六进制 0、1、2、3、4、5、6、7、8、9、A、B、C、D、E、F 逢十六进一

    在C语言中, 如果想用十六进制表示某个数, 前面需要加上0x;

    注意点:

    %i %d代表以十进制输出整数

    0x 和 0X写法 一样, 0b和0B写法也一样

    // 12的不同进制的表达

    // 用十进制来表示

    int num1 = 12;

    printf("num1 = %i\n", num1);

    // 用十六进制来表示

    int num2 = = 0xc;

    printf("num2 = %i\n", num2);

    // 用八进制来表示

    int num3 = 014;

    printf("num3 = %i\n", num3);

    // 用二进制来表示

    int num4 = 0b1100;

    printf("num4 = %i\n", num4);

    // 不同进制的输出

    int num = 12;

    // 以十进制输出

    printf("%i\n", num);

    // 以八进制输出

    printf("%o\n", num);

    // 以十六进制输出

    printf("%x\n", num);

    //二进制

    void printBinary(char value){

    }

    进制转换

    十进制转二进制

    除2取余, 余数倒序; 得到的序列就是二进制表示形式

    /*

    * 求12的二进制数

    * 12

    * 2

    * ----

    * 6 0

    * 2

    * ----

    * 3 0

    * 2

    * ----

    * 1 1

    * 2

    * ----

    * 0 1

    *

    * 12 --> 1100

    */

    二进制转十进制

    规则: 系数 * 基数^(索引)

    系数:就是每一位对应的值就是系数;

    基数: 如果是二进制转到十进制,那么2就是基数

    -如果是从八进制转换到十进制, 那么八就是基数

    索引:从最低位以0开始,依次递增;

    /*

    1*2^3 + 1*2^2 + 0*2^1 + 0*2^0

    1 1 0 0

    ==> 8 + 4 + 0 + 0 = 12

    */

    /*

    * 二进制快速转换十进制

    * 64 32 16 8 4 2 1

    * 1 1 1 1 1 1 1

    */

    十进制转换八进制

    规则: 除8取余,余数倒数

    /* 十进制24转换为八进制

    *

    * 24

    * 8

    * ---

    * 3 0

    * 8

    * ---

    * 0 3

    *

    * 24 --> 30

    */

    二进制转换为八进制

    必须知道:在八进制中最大的数字是7

    1.可以使用系数 * 基数^(索引) 将二进制转换为8进制

    2.二进制在转换为8进制的时候,把三个二进制数看做一个八进制位即可

    /*从右至左每3位划分为8进制的1位, 不够前面补0

    001 100 100

    第0位: 100 等于十进制 4

    第1位: 100 等于十进制 4

    第2位: 001 等于十进制 1

    最终结果: 144就是转换为8进制的值

    /*

    二进制转换为十六进制

    二进制在转换为十六进制的时候,把四个二进制位看做一个十六进制为即可

    /*

    3 8

    0011 1000 ==> 0x38

    */

    十进制小数转换为二进制小数

    整数部分,直接转换为二进制即可

    小数部分,使用"乘2取整,顺序排列"

    用2乘十进制小数,可以得到积,将积的整数部分取出,再用2乘余下的小数部分,直到积中的小数部分为零,或者达到所要求的精度为止

    然后把取出的整数部分按顺序排列起来, 即是小数部分二进制

    最后将整数部分的二进制和小数部分的二进制合并起来, 即是一个二进制小数

    例如: 将12.125转换为二进制

    // 整数部分(除2取余)

    12

    / 2

    ------

    6 // 余0

    / 2

    ------

    3 // 余0

    / 2

    ------

    1 // 余1

    / 2

    ------

    0 // 余1

    //12 --> 1100

    // 小数部分(乘2取整数积)

    0.125

    * 2

    ------

    0.25 //0

    0.25

    * 2

    ------

    0.5 //0

    0.5

    * 2

    ------

    1.0 //1

    0.0

    // 0.125 --> 0.001

    // 12.8125 --> 1100.001

    二进制转换为十进制小数

    整数部分按照二进制转十进制即可

    小数部分从最高位开始乘以2的负n次方, n从1开始

    例如: 将 1100.001转换为十进制

    // 整数部分(乘以2的n次方, n从0开始)

    0 * 2^0 = 0

    0 * 2^1 = 0

    1 * 2^2 = 4

    1 * 2^3 = 8

    // 1100 == 8 + 4 + 0 + 0 == 12

    // 小数部分(乘以2的负n次方, n从0开始)

    0 * (1/2) = 0

    0 * (1/4) = 0

    1 * (1/8) = 0.125

    // .100 == 0 + 0 + 0.125 == 0.125

    // 1100.001 --> 12.125

    将0.8125转换为二进制

    0.8125

    * 2

    --------

    1.625 // 1

    0.625

    * 2

    --------

    1.25 // 1

    0.25

    * 2

    --------

    0.5 // 0

    * 2

    --------

    1.0 // 1

    0.0

    // 0. 8125 --> 0.1101

    原码 补码 反码之间的关系

    正数的原码 = 补码 = 反码 ; (三码合一);

    int 类型在计算机中占用4个字节

    1个字节等于8位,所以int类型总共占用32位;

    注意点:

    在存储正整数的时候,第一个(最高位)是符号位, 0是代表正数, 1代表是负数;

    0000 0000 0000 0000 0000 0000 0000 1100

    // int num = 12;

    负整数的原码, 补码, 反码

    // int num = -12;

    原码 : 二进制,将最高位变为1;

    1000 0000 0000 0000 0000 0000 0000 1100

    反码 : 除了符号位以外, 0变1, 1变0;

    1000 0000 0000 0000 0000 0000 0000 1100 12的反码

    补码 : 反码 + 1

    1111 1111 1111 1111 1111 1111 1111 0011 12的反码

    + 0000 0000 0000 0000 0000 0000 0000 0001 +1

    ----------------------------------------

    1111 1111 1111 1111 1111 1111 1111 0100 12的补码

    // 注意点: 无论是正整数还是负整数,存储在计算机中都是补码

    如果只有原码参与运算会出现什么问题

    // 1 - 1; 1 + (-1);

    0000 0000 0000 0000 0000 0000 0000 0001 // 1原码

    +1000 0000 0000 0000 0000 0000 0000 0001 // -1原码

    ---------------------------------------

    1000 0000 0000 0000 0000 0000 0000 0010 == -2

    很明显,上面的运算结果不成立

    计算机只能做就加法运算,而且是做补码运算;

    /*

    * 1 - 1 理解为 1 + (-1)

    * 0000 0000 0000 0000 0000 0000 0000 0001 1补码就是原码

    *

    // 求-1的补码

    * 1000 0000 0000 0000 0000 0000 0000 0001 -1源码

    * 1111 1111 1111 1111 1111 1111 1111 1110 -1反码

    * 0000 0000 0000 0000 0000 0000 0000 0001

    * -----------------------------------------

    * 1111 1111 1111 1111 1111 1111 1111 1111 -1补码

    *

    *

    * 0000 0000 0000 0000 0000 0000 0000 0001 1补码

    * + 1111 1111 1111 1111 1111 1111 1111 1111 -1补码

    * -------------------------------------------

    * 0000 0000 0000 0000 0000 0000 0000 0000 0

    */

    /*

    * 4 - 6 --> 4 + (-6)

    * 0000 0000 0000 0000 0000 0000 0000 0100 4补码

    *

    * 1000 0000 0000 0000 0000 0000 0000 0110 -6源码

    * 1111 1111 1111 1111 1111 1111 1111 1001 -6反码

    * 0000 0000 0000 0000 0000 0000 0000 0001

    * -------------------------------------------

    * 1111 1111 1111 1111 1111 1111 1111 1010 -6补码

    *

    *

    *

    * 0000 0000 0000 0000 0000 0000 0000 0100 4补码

    * 1111 1111 1111 1111 1111 1111 1111 1010 -6补码

    * 1111 1111 1111 1111 1111 1111 1111 1110 补码的结果

    *

    * 注意点: 当前计算出来的是正确结果的补码, 要想知道正确结果是多少, 需要将补码转换为源码

    // 原码 = (补码 - 1)再求其反码

    *

    * 1111 1111 1111 1111 1111 1111 1111 1110 结果的补码

    * 0000 0000 0000 0000 0000 0000 0000 0001 减1

    * -------------------------------------------

    * 1111 1111 1111 1111 1111 1111 1111 1101 结果的反码

    * 1000 0000 0000 0000 0000 0000 0000 0010 结果的源码 -2

    */

    /*

    0101

    + 0001

    -----

    0102 --> 0110

    0110 --> 0102

    - 0001 0001

    ---------------

    0101

    */

    位运算符

    符号

    名称

    运算结果

    &

    按位与

    同1为1

    |

    按位或

    有1为1

    ^

    按位异或

    不同为1

    ~

    按位取反

    0变1,1变0

    <<

    按位左移

    乘以2的n次方

    >>

    按位右移

    除以2的n次方

    & 按位与

    规则: 两个都是真(1)时,结果才是真(1);

    规律:任何一位和1相与,结果还是原来的那一位;

    /*

    * 9 & 3 = ?

    * 0000 0000 0000 0000 0000 0000 0000 1001 // 9的补码

    * & 0000 0000 0000 0000 0000 0000 0000 0011 // 3的补码

    * -----------------------------------------------

    * 0000 0000 0000 0000 0000 0000 0000 0001 // 1

    *

    * 12 & 8

    * 0000 0000 0000 0000 0000 0000 0000 1100 //12的补码

    *& 0000 0000 0000 0000 0000 0000 0000 1000 //8的补码

    * -----------------------------------------------

    * 0000 0000 0000 0000 0000 0000 0000 1000 //4

    */

    应用: 判断奇数偶数

    int num = 4;

    // if(1 == (num & 1)){

    // printf("%i是奇数\n", num);

    // }else{

    // printf("%i是偶数\n", num);

    // }

    if(num & 1){

    printf("%i是奇数\n", num);

    }else{

    printf("%i是偶数\n", num);

    }

    | 按位或

    只要对应的二个二进位有一个为1时,结果位就为1,否则为0

    /* 9 | 3 = ?

    * 0000 0000 0000 0000 0000 0000 0000 1001 // 9的补码

    *| 0000 0000 0000 0000 0000 0000 0000 0011 // 3的补码

    * -----------------------------------------------

    * 0000 0000 0000 0000 0000 0000 0000 1011 // 11

    */

    ~ 按位取反

    规则:0变1, 1变0 ;

    /* ~9 = ?

    * 0000 0000 0000 0000 0000 0000 0000 1001 // 9的补码

    *~1111 1111 1111 1111 1111 1111 1111 0110 // 结果的补码

    * 0000 0000 0000 0000 0000 0000 0000 0001

    * -------------------------------------------

    * 1111 1111 1111 1111 1111 1111 1111 0101 // 结果补码的反码

    * 1000 0000 0000 0000 0000 0000 0000 1010 // 结果的源码 -10

    */

    ^ 按位异或

    规则: 相同为0,不同为1;

    /* 9 ^ 3 = ?

    * 0000 0000 0000 0000 0000 0000 0000 1001 // 9的补码

    *^0000 0000 0000 0000 0000 0000 0000 0011 // 3的补码

    *-------------------------------------------

    * 0000 0000 0000 0000 0000 0000 0000 1010 // 10

    */

    规律:

    任何两个相同的值异或之后的结果都是0;

    任何一个数和0异或之后的结果还是那个数

    任何一个数异或另外一个数两次之后,结果还是那个数;

    应用场景:简单的加密

    int pwd = 123456789;

    int res = pwd ^ 998;

    printf("加密之前: %i\n", pwd);

    printf("加密之后: %i\n", res);

    int res2 = res ^ 998;

    printf("解密之后: %i\n", res2);

    交换两个数的值(按位异或)(任何一个数异或另外一个数两次之后,结果还是那个数;)

    /*

    * 需求: 交换两个变量的值

    *

    * int a = 10; int b = 20;

    */

    int a = 10;

    int b = 20;

    printf("交换之前a = %i, b = %i\n", a, b);

    // a = a ^ b;

    // b = a ^ b; // b = a ^ (b ^ b) = a; b = 10;

    // a = a ^ b; // a = (a ^ a) ^ b = b; a = 20;

    b = a ^ b;

    a = a ^ b; // a = a ^ a ^ b; a = b; a = 20;

    b = a ^ b; // b = a ^ b ^ b; b = a; a = 10;

    printf("交换之后a = %i, b = %i\n", a, b);

    --------------------------------------------------------

    // 之前学的

    // 重点掌握

    // int temp = a;

    // a = b;

    // b = temp;

    // printf("交换之后a = %i, b = %i\n", a, b);

    // a = a + b; // a = 10 + 20; a = 30;

    // b = a - b; // b = 30 - 20; b = 10;

    // a = a - b; // a = 30 - 10; a = 20;

    // printf("交换之后a = %i, b = %i\n", a, b);

    按位左移 <<

    移动规则:从符号位开始整体移动,多余的砍掉,缺少的用零补

    计算规律: 一个数左移多少位,就是这个数乘以2的多少次幂

    应用场景: 在企业开发中一旦想要某个数乘以2的多少次幂, 就要想到左移

    例如: 9 * 2(1) = 18 ; 9 * 2(2) = 36

    9 << 1

    0000 0000 0000 0000 0000 0000 0000 0000 // 位置参考

    000 0000 0000 0000 0000 0000 0000 10010 // 9的补码

    按位右移 <<

    移动规则: 除符号位以外整体右移,多出来的砍掉,缺少的用符号位填充;

    计算规则: 一个正数右移多少位,就是这个数除以2的n次幂;

    /*

    // 9 >> 1

    0000 0000 0000 0000 0000 0000 0000 0000 // 位置参考

    00000 0000 0000 0000 0000 0000 0000 100 --> 4

    */

    printf("%i\n", 9 >> 1);

    // -9 >> 1

    /*

    * 1000 0000 0000 0000 0000 0000 0000 1001 // -9源码

    * 1111 1111 1111 1111 1111 1111 1111 0110 // -9反码

    * 1111 1111 1111 1111 1111 1111 1111 0111 // -9补码

    *

    0000 0000 0000 0000 0000 0000 0000 0000 // 位置参考

    11111 1111 1111 1111 1111 1111 1111 011 // 右移完毕的结果, 补码

    0000 0000 0000 0000 0000 0000 0000 0001

    11111 1111 1111 1111 1111 1111 1111 010 // 右移完毕的结果, 反码

    10000 0000 0000 0000 0000 0000 0000 101 // 右移完毕的结果, 源码

    */

    printf("%i\n", -9 >> 1);

    变量的内存分析

    内存是连续的;

    内存地址从大到小;

    计算机会从内存地址大的开始分配内存(内存寻址从大到小);

    也就是说先定义的变量内存地址大于后定义的变量;

    变量的存储原则:

    先分配字节地址大内存,然后分配字节地址小的内存(内存寻址是从大到小),

    变量的首地址,是变量所占存储空间字节地址(最小的那个地址)

    低位保存在地地址字节上,高位保存在高地址字节上;

    9a52d679d1ad

    image

    定义变量

    定义变量的目的就是为了在内存中开辟一块存储空间;

    定义变量时指定数据类型的目的就是为了告诉计算机需要开辟多大的空间

    char在内存中占用一个字节,int在内存中占用4个字节,double在内存中占用8字节(一个字节 = 8 位);

    sizeof(char); sizeof(int); sizeof(double)

    由于计算机只能识别0,1,所以会把十进制转换为二进制

    给变量分配内存的时候是从内存地址比较大的开始存储;

    char类型内存存储细节

    %p 是专门用于输出变量地址的

    & 是专门用于取出变量地址;

    int num1 = 10;

    int num2 = 20;

    printf("num1 = %p\n", &num1);

    printf("num2 = %i\n", &num2);

    char类型基本概念

    char是c语言中比较灵活的一种数据类型,称为"字符型"

    char类型变量占1个字节存储空间, 共8位;

    除单个字符以外,C语言的转移字符也可以利用char类型存储;

    字符

    意义

    \b

    退格(BS)当前位置向后回退一个字符

    \r

    回车(CR),将当前位置移至本行开头

    \n

    换行(LF),将当前位置移至下一行开头

    \t

    水平制表(HT),跳到下一个TAB 位置

    \0

    用于表示字符串的结束标记

    \

    代表一个反斜线字符 \

    "

    代表一个双引号字符 "

    '

    代表一个单引号字符 '

    char类型的注意点:

    char类型占一个字节,所以只有8位可以存储

    ASCII码表中字符对应的ASCII值是从0~127

    char类型的取值范围 -2^7 ~ 2^7 // -128 ~ 127

    一个中文字符占3字节(unicode表),所有char不可以存储中文

    char c = '我'; // 错误写法

    除转义字符以外,不支持多个字符

    char ch = 'ab'; // 错误写法

    char 类型存储字符时会先查找对应的ASCII码值,存储的是ASCII值,所以字符6和数字6存储的内容不同;

    char ch1 = '6'; // 存储的是ASCII码 64;

    char ch2 = 6 ; // 存储的是数字 6;

    类型说明符

    类型说明符易班都是用于修饰int 类型所以在使用时可以省略int ;

    说明长度的:

    short 短整型

    long 长整型

    long long

    char ch;

    short int num1;

    int num2;

    long int num3;

    long long int num4;

    printf("ch = %i\n", sizeof(ch)); // 1

    printf("short = %i\n", sizeof(num1)); // 2

    printf("int = %i\n", sizeof(num2)); // 4

    printf("long = %i\n", sizeof(num3)); // 4

    printf("long long = %i\n", sizeof(num4)); // 8

    C语言不看怎么存,只看怎么取;

    short num5 = 123;

    printf("num5 = %lld\n", num5);

    long num6 = 123;

    printf("num6 = %lld\n", num6);

    long long num7 = 123;

    printf("num7 = %lld\n", num7); // 123

    short 和long

    int占用4个字节(32bit),取值范围是-2^31 ~ 2^31-1;

    short占用2个字节(16bit),取值范围是-2^15 ~ 2^15-1

    long int 在32位编译器中占用4个字节;

    在64位编译器中,long占用8个字节(64bit),取值范围是-2^63 ~ 2^63-1

    注意点:

    如果存储的数据超出了类型对应的取值范围,那么就会导致存储的数据不对

    由于内存非常有限,所以在编写程序的时候,尽量合理的定义变量

    short的长度不能大于 int , int的长度不能大于long

    char 一定为8位(1个字节),毕竟char是我们变成能用的最小数据类型;

    说明符号位的:

    signed 有符号型(默认int就是有符号的 默认的,一般用不上);

    unsigned 无符号型

    不把二进制的第一位当做符号位来使用,

    所以只能存储零和正数,不能存储负数

    注意点: 如果变量被unsigned修饰了,那么取出的时候必须使用%u,%u就代表用无符号;

    对于整数而言,在内存中二进制的第一位就是符号位

    如果第一位是0,代表正数;第一位是1,代表负数;

    默认情况下所有的int 类型都是有符号的,也就是都会将第一位看做符号位;

    展开全文
  • 二进制浮点数以及二进制浮点数算术运算二进制浮点数表示半精度浮点数单精度浮点数双精度浮点数特殊情况浮点数的运算步骤一、对阶二、尾数运算三、结果规格化左规操作右规操作四、 舍入处理五、 溢出判断六、例子...

    二进制浮点数表示

    在这里插入图片描述
    阶码(指数)就是指数位存储的值,而偏阶(移码)则不同精度的浮点数的偏阶也各不相同,具体可以查看指数偏差
    B i a s = 2 k − 1 − 1 Bias=2^{k-1}-1 Bias=2k11, 其中k是指数中的位数。

    半精度浮点数

    半精度浮点数 是一种被计算机使用的二进制浮点数据类型。半精度浮点数使用2个字节(16位)来存储。
    在IEEE 754-2008中,它被称作binary16。这种数据类型只适合存储对精度要求不高的数字,不适合用来计算。

    IEEE 754 标准指定了一个 binary16 要有如下的格式:
    Sign bit(符号位): 1 bit
    Exponent width(指数位宽): 5 bits
    Significand precision(尾数精度): 11 bits (有10位被显式存储)

    按如下顺序排列:
    在这里插入图片描述
    除非指数位全是0,否则就会假定隐藏的起始位是1。因此只有10位尾数在内存中被显示出来,而总精度是11位。据IEEE 754的说法,虽然尾数只有10位,但是尾数精度是11位的(log10(211) ≈ 3.311 十进制数).

    单精度浮点数

    单精度浮点数 格式是一种数据类型,在计算机存储器中占用4个字节(32 bits),利用“浮点”(浮动小数点)的方法,可以表示一个范围很大的数值。

    第1位表示正负,中间8位表示指数,后23位储存有效数位(有效数位是24位)。

    第一位的正负号0代表正,1代表负。

    中间八位共可表示 2 8 = 256 2^8=256 28=256个数,指数可以是二补码;或0到255,0到126代表-127到-1,127代表零,128-255代表1-128。

    有效数位最左手边的1并不会储存,因为它一定存在(二进制的第一个有效数字必定是1)。换言之,有效数位是24位,实际储存23位。

    在这里插入图片描述
    s i g n = + 1 sign = +1 sign=+1
    e x p o n e n t = ( − 127 ) + 124 = − 3 exponent = (-127)+124=-3 exponent=(127)+124=3
    f r a c t i o n = 1 + 2 − 2 = 1.25 fraction=1+2^{-2}=1.25 fraction=1+22=1.25
    v a l u e = ( + 1 ) × 1.25 × 2 − 3 = + 0.15625 value=(+1)\times1.25\times2^{-3}=+0.15625 value=(+1)×1.25×23=+0.15625

    双精度浮点数

    双精度浮点数(double)是计算机使用的一种资料类型。比起单精度浮点数,双精度浮点数(double)使用 64 位(8字节) 来存储一个浮点数。 它可以表示二进位制的53位有效数字,其可以表示的数字的绝对值范围为 [ 2 − 1024 , 2 1024 ] [2^{-1024}, 2^{1024}] [21024,21024]
    在这里插入图片描述

    特殊情况

    以双精度浮点数为例,说明一些特殊情况
    在这里插入图片描述

    当指数exponent全为0或者全为1时,有特殊含义,有以下四种情况,
    1、 e x p o n e n t = 0 , f r a c t i o n = 0 ⇒ ± 0 exponent=0, fraction=0 \Rightarrow \pm0 exponent=0,fraction=0±0
    2、 e x p o n e n t = 0 , f r a c t i o n ≠ 0 ⇒ 非 正 规 形 式 的 浮 点 数 exponent=0, fraction\neq0 \Rightarrow 非正规形式的浮点数 exponent=0,fraction=0
    3、 e x p o n e n t = 2047 , f r a c t i o n = 0 ⇒ ± ∞ exponent=2047, fraction=0 \Rightarrow \pm\infty exponent=2047,fraction=0±
    4、 e x p o n e n t = 2047 , f r a c t i o n ≠ 0 ⇒ N a N exponent=2047, fraction\neq0 \Rightarrow NaN exponent=2047,fraction=0NaN

    在这里插入图片描述

    浮点数的运算步骤

    浮点数的加减运算一般由以下五个步骤完成:对阶、尾数运算、规格化、舍入处理、溢出判断

    一、对阶

    所谓对阶是指将两个进行运算的浮点数的阶码对齐的操作。对阶的目的是为使两个浮点数的尾数能够进行加减运算。因为,当进行 M x ⋅ 2 E x M_x·2^{E_x} Mx2Ex M y ⋅ 2 E y M_y·2^{E_y} My2Ey加减运算时,只有使两浮点数的指数值部分相同,才能将相同的指数值作为公因数提出来,然后进行尾数的加减运算。对阶的具体方法是:首先求出两浮点数阶码的差,即 Δ E = E x − E y \Delta E = E_x - E_y ΔE=ExEy,将小阶码加上 Δ E \Delta E ΔE,使之与大阶码相等,同时将小阶码对应的浮点数的尾数右移相应位数,以保证该浮点数的值不变。几点注意:

    (1)对阶的原则是小阶对大阶,之所以这样做是因为若大阶对小阶,则尾数的数值部分的高位需移出,而小阶对大阶移出的是尾数的数值部分的低位,这样损失的精度更小。

    (2)若 Δ E \Delta E ΔE=0,说明两浮点数的阶码已经相同,无需再做对阶操作了。

    (3)采用补码表示的尾数右移时,符号位保持不变。

    (4)由于尾数右移时是将最低位移出,会损失一定的精度,为减少误差,可先保留若干移出的位,供以后舍入处理用。

    二、尾数运算

    尾数运算就是进行完成对阶后的尾数相加减。这里采用的就是我们前面讲过的纯小数的定点数加减运算。

    三、结果规格化

    在机器中,为保证浮点数表示的唯一性,浮点数在机器中都是以规格化形式存储的。对于IEEE754标准的浮点数来说,就是尾数必须是1.M的形式。由于在进行上述两个定点小数的尾数相加减运算后,尾数有可能是非规格化形式,为此必须进行规格化操作。

    规格化操作包括左规和右规两种情况。

    左规操作

    将尾数左移,同时阶码减值,直至尾数成为 1. M 1.M 1.M的形式。例如,浮点数 0.0011 ∗ 2 5 0.0011*2^5 0.001125是非规格化的形式,需进行左规操作,将其尾数左移3位,同时阶码减3,就变成 1.1100 ∗ 2 2 1.1100*2^2 1.110022规格化形式了。

    右规操作

    将尾数右移1位,同时阶码增1,便成为规格化的形式了。要注意的是,右规操作只需将尾数右移一位即可,这种情况出现在尾数的最高位(小数点前一位)运算时出现了进位,使尾数成为 10. x x x x 10.xxxx 10.xxxx 11. x x x x 11.xxxx 11.xxxx的形式。例如, 10.0011 ∗ 2 5 10.0011*2^5 10.001125右规一位后便成为 1.00011 ∗ 2 6 1.00011*2^6 1.0001126的规格化形式了。

    四、 舍入处理

    浮点运算在对阶或右规时,尾数需要右移,被右移出去的位会被丢掉,从而造成运算结果精度的损失。为了减少这种精度损失,可以将一定位数的移出位先保留起来,称为保护位,在规格化后用于舍入处理。

    IEEE754标准列出了四种可选的舍入处理方法:

    (1)就近舍入(round to nearest)这是标准列出的默认舍入方式,其含义相当于我们日常所说的“四舍五入”。例如,对于32位单精度浮点数来说,若超出可保存的23位的多余位大于等于 100 … 01 100…01 10001,则多余位的值超过了最低可表示位值的一半,这种情况下,舍入的方法是在尾数的最低有效位上加1;若多余位小于等于 011 … 11 011…11 01111,则直接舍去;若多余位为 100 … 00 100…00 10000,此时再判断尾数的最低有效位的值,若为0则直接舍去,若为1则再加1。

    (2) + ∞ +∞ +舍入(round toward + ∞ +∞ +)对正数来说,只要多余位不为全0,则向尾数最低有效位进1;对负数来说,则是简单地舍去。

    (3) − ∞ -∞ 舍入(round toward − ∞ -∞ )与朝 + ∞ +∞ +舍入方法正好相反,对正数来说,只是简单地舍去;对负数来说,只要多余位不为全0,则向尾数最低有效位进1。

    (4)朝0舍入(round toward 0)

    即简单地截断舍去,而不管多余位是什么值。这种方法实现简单,但容易形成累积误差,且舍入处理后的值总是向下偏差。

    五、 溢出判断

    与定点数运算不同的是,浮点数的溢出是以其运算结果的阶码的值是否产生溢出来判断的。若阶码的值超过了阶码所能表示的最大正数,则为上溢,进一步,若此时浮点数为正数,则为正上溢,记为 + ∞ +∞ +,若浮点数为负数,则为负上溢,记为 − ∞ -∞ ;若阶码的值超过了阶码所能表示的最小负数,则为下溢,进一步,若此时浮点数为正数,则为正下溢,若浮点数为负数,则为负下溢。正下溢和负下溢都作为0处理。

    要注意的是,浮点数的表示范围和补码表示的定点数的表示范围是有所不同的,定点数的表示范围是连续的,而浮点数的表示范围可能是不连续的。

    六、例子

    f l o a t      a = 0.3 ; b = 1.6 float \ \ \ \ a=0.3;b=1.6 float    a=0.3;b=1.6;

    a = ( 0.3 ) 10 = ( 0011   1110   1001   1001   1001   1001   1001   1010 ) 2 a=(0.3)_{10}=(0011\ 1110\ 1001\ 1001\ 1001\ 1001\ 1001\ 1010)_2 a=(0.3)10=(0011 1110 1001 1001 1001 1001 1001 1010)2
    S a = 0      E a = 011   1110   1      M a = 1.001   1001   1001   1001   1001   1010 S_a=0\ \ \ \ E_a=011\ 1110\ 1\ \ \ \ M_a=1.001\ 1001\ 1001\ 1001\ 1001\ 1010 Sa=0    Ea=011 1110 1    Ma=1.001 1001 1001 1001 1001 1010

    b = ( 1.6 ) 10 = ( 0011   1111   1100   1100   1100   1100   1100   1101 ) 2 b=(1.6)_{10}=(0011\ 1111\ 1100\ 1100\ 1100\ 1100\ 1100\ 1101)_2 b=(1.6)10=(0011 1111 1100 1100 1100 1100 1100 1101)2
    S b = 0      E b = 011   1111   1     M b = 1.100   1100   1100   1100   1100   1101 S_b=0\ \ \ \ E_b=011\ 1111\ 1\ \ \ M_b=1.100\ 1100\ 1100\ 1100\ 1100\ 1101 Sb=0    Eb=011 1111 1   Mb=1.100 1100 1100 1100 1100 1101

    a + b = ? a+b=? a+b=?

    二进制浮点数加法

    第一步:对阶

    ∵ E a < E b     E b − E a = 2 ∵ E_a < E_b\ \ \ E_b-E_a=2 Ea<Eb   EbEa=2

    ∴ M a 要 调 整 为 0.0   1001   1001   1001   1001   1001   10         10 ∴ Ma要调整为 0.0\ 1001\ 1001\ 1001\ 1001\ 1001\ 10\ \ \ \ \ \ \ 10 Ma0.0 1001 1001 1001 1001 1001 10       10

    E = 011    1111    1 E=011\ \ 1111\ \ 1 E=011  1111  1

    第二步:尾数运算

         0.01001100110011001100110 \ \ \ \ 0.01001100110011001100110     0.01001100110011001100110
    +   1.10011001100110011001101 +\ 1.10011001100110011001101 + 1.10011001100110011001101
    = 1.11100110011001100110011 =1.11100110011001100110011 =1.11100110011001100110011

    第三步:规格化

    1.11100110011001100110011 1.11100110011001100110011 1.11100110011001100110011‬已经是个规格化数据了

    第四步:舍入处理

    由于在对阶时, M a M_a Ma有右移,且第一次最高为1,第二次为0,所以按"0舍1入",尾数运算结果调整为 1.11100110011001100110100 1.11100110011001100110100 1.11100110011001100110100

    第五步:溢出判断

    没有溢出,阶码不调整,所以最后的结果为

    a + b = ( 0    01111111    11100110011001100110100 ) 2 = ( 0011   1111   1111   0011   0011   0011   0011   0100 ) 2 = ( 3 F F 33334 ) 16 a+b=(0\ \ 01111111\ \ 11100110011001100110100)_2=(0011\ 1111\ 1111\ 0011\ 0011\ 0011\ 0011\ 0100)_2=(3FF33334)_{16} a+b=(0  01111111  11100110011001100110100)2=(0011 1111 1111 0011 0011 0011 0011 0100)2=(3FF33334)16

    转为10进制

    a + b = 1.90000010 a+b=1.90000010 a+b=1.90000010

    二进制浮点数减法

    b − a = ? b-a=? ba=?
    第一步:对阶

    跟上面加法一样

    第二步:尾数运算

         1.10011001100110011001101 \ \ \ \ 1.10011001100110011001101     1.10011001100110011001101

    −   0.01001100110011001100110 -\ 0.01001100110011001100110  0.01001100110011001100110

    = 1.01001100110011001100111 =1.01001100110011001100111 =1.01001100110011001100111

    第三步:规格化

    1.01001100110011001100111 1.01001100110011001100111 1.01001100110011001100111已经是个规格化数据了

    第四步:舍入处理

    由于在对阶时, M a M_a Ma有右移,且第一次最高为1,第二次为0,所以按"0舍1入",尾数运算结果调整为 1.01001100110011001100110 1.01001100110011001100110 1.01001100110011001100110

    第五步:溢出判断

    没有溢出,阶码不调整,所以最后的结果为

    a − b = ( 0    01111111    01001100110011001100110 ) 2 = ( 0011    1111    1010    0110    0110    0110    0110    0110 ) 2 = ( 3 F A 66666 ) 16 a-b=(0\ \ 01111111\ \ 01001100110011001100110)2=(0011\ \ 1111\ \ 1010\ \ 0110\ \ 0110\ \ 0110\ \ 0110\ \ 0110)_2=(3FA66666)_{16} ab=(0  01111111  01001100110011001100110)2=(0011  1111  1010  0110  0110  0110  0110  0110)2=(3FA66666)16

    转为10进制

    a − b = 1.29999995 a-b=1.29999995 ab=1.29999995

    二进制浮点数乘法

    浮点数的乘法分为以下几个步骤:

    计算符号位:通过异或操作计算符号位,若两个操作数符号位相同,则结果符号位为0,否则结果符号为1
    计算原始尾数:两个操作数的尾数相乘(注意,这里是1.M * 1.M),得到原始尾数
    计算原始指数:将两个操作数的指数(这里指的是指数幂次方,也就是阶码-移码后得到的数)相加,得到原始指数
    规格化与舍入:对原始尾数和原始指数进行规格化,获得结果的指数,再对尾数进行舍入,获得结果的尾数

    f l o a t      X = − 0.3 ; Y = 500.25 float \ \ \ \ X=-0.3;Y=500.25 float    X=0.3;Y=500.25;

    X = ( − 0.3 ) 10 = ( 0.010011001100110011... 循 环 ) 2 = ( 1.00110011... 循 环 ) 2 ∗ 2 − 2 = ( 1    01111101    00110011001100110011010 ) 2 ( 这 里 对 无 限 循 环 小 数 有 舍 入 处 理 ) X=(-0.3)_{10}=(0.010011001100110011...循环)_{2}=(1.00110011...循环)_2 * 2^{-2}=(1\ \ 01111101\ \ 00110011001100110011010)_2(这里对无限循环小数有舍入处理) X=(0.3)10=(0.010011001100110011...)2=(1.00110011...)222=(1  01111101  00110011001100110011010)2()
    Y = ( 500.25 ) 10 = ( 111110100.01 ) 2 = ( 1.1111010001 ) 2 ∗ 2 8 = ( 0    10000111    11110100010000000000000 ) 2 Y=(500.25)_{10}=(111110100.01)_2=(1.1111010001)_2*2^{8}=(0\ \ 10000111\ \ 11110100010000000000000)_2 Y=(500.25)10=(111110100.01)2=(1.1111010001)228=(0  10000111  11110100010000000000000)2

    X ∗ Y = ( X s ∗ Y s ) ∗ 2 X E + Y E X*Y=(X_s*Y_s)*2^{X_E+Y_E} XY=(XsYs)2XE+YE
    X E = − 2             X s = 1.00110011001100110011010 X_E=-2\ \ \ \ \ \ \ \ \ \ \ X_s=1.00110011001100110011010 XE=2           Xs=1.00110011001100110011010
    Y E = 8                  Y s = 1.1111010001 Y_E=8\ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ Y_s=1.1111010001 YE=8                Ys=1.1111010001
       X s          1.0011001100110011001101 \ \ X_s\ \ \ \ \ \ \ \ 1.0011001100110011001101   Xs        1.0011001100110011001101
    ∗   Y s      ∗                          1.1111010001 *\ Y_s\ \ \ \ *\ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ 1.1111010001  Ys                            1.1111010001
    = 10.01011000010011001100111001011101 =10.01011000010011001100111001011101 =10.01011000010011001100111001011101

    X ∗ Y = 10.01011000010011001100111001011101 ∗ 2 6 X*Y=10.01011000010011001100111001011101*2^6 XY=10.0101100001001100110011100101110126
                 = 1.001011000010011001100111001011101 ∗ 2 7 ( 右 规 操 作 ) \ \ \ \ \ \ \ \ \ \ \ \ =1.001011000010011001100111001011101*2^7(右规操作)             =1.00101100001001100110011100101110127()

    结果二进制就为(注意,上面的指数7要加上移码才是存在指数位中的阶码,即7+127=134)
    ( 1    10000110    00101100001001100110100 ) 2 (1\ \ 10000110\ \ 00101100001001100110100)_2 (1  10000110  00101100001001100110100)2
    至于最后的尾数是怎么得到,是由原始尾数(X和Y的尾数相乘后得到)经过舍入得到

    二进制浮点数除法

    除法与乘法相差不大,变更为指数相减,尾数相除。

    f l o a t      X = 91.34375 ; Y = 0.14453125 float \ \ \ \ X=91.34375;Y=0.14453125 float    X=91.34375;Y=0.14453125;

    X = ( 91.34375 ) 10 = ( 1011011.01011 ) 2 = ( 1.01101101011 ) 2 ∗ 2 6 = ( 0    10000101    01101101011000000000000 ) 2 X=(91.34375)_{10}=(1011011.01011)_{2}=(1.01101101011)_2 * 2^{6}=(0\ \ 10000101\ \ 01101101011000000000000)_2 X=(91.34375)10=(1011011.01011)2=(1.01101101011)226=(0  10000101  01101101011000000000000)2
    Y = ( 0.14453125 ) 10 = ( 0.00100101 ) 2 = ( 1.00101 ) 2 ∗ 2 8 = ( 0    01111100    00101000000000000000000 ) 2 Y=(0.14453125)_{10}=(0.00100101)_2=(1.00101)_2*2^{8}=(0\ \ 01111100\ \ 00101000000000000000000)_2 Y=(0.14453125)10=(0.00100101)2=(1.00101)228=(0  01111100  00101000000000000000000)2

    X / Y = ( X s / Y s ) ∗ 2 X E − Y E = ( X s / Y s ) ∗ 2 6 − ( − 3 ) X/Y=(X_s/Y_s)*2^{X_E-Y_E}=(X_s/Y_s)*2^{6-(-3)} X/Y=(Xs/Ys)2XEYE=(Xs/Ys)26(3)
    X E = 6                   X s = 1.01101101011 X_E=6\ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ X_s=1.01101101011 XE=6                 Xs=1.01101101011
    Y E = − 3                  Y s = 1.00101 Y_E=-3\ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ Y_s=1.00101 YE=3                Ys=1.00101
       X s          1.01101101011 \ \ X_s\ \ \ \ \ \ \ \ 1.01101101011   Xs        1.01101101011
    /   Y s      /    1.00101 /\ Y_s\ \ \ \ /\ \ 1.00101 / Ys    /  1.00101
    = 1.001111 =1.001111 =1.001111

    9 + 127 = 136 9+127 = 136 9+127=136

    ( 0    10001000    00111100000000000000000 ) 2 (0\ \ 10001000\ \ 00111100000000000000000)_2 (0  10001000  00111100000000000000000)2

    浮点运算逻辑电路

    在这里插入图片描述

    在这里插入图片描述

    Reference

    https://zhuanlan.zhihu.com/p/58731780
    https://www.yuejianzun.xyz/2019/05/28/%E6%B5%AE%E7%82%B9%E6%95%B0%E5%A4%84%E7%90%86/
    https://www.cnblogs.com/yilang/
    https://www.youtube.com/watch?v=MiOtePebraQ
    https://www.youtube.com/watch?v=27JjUa-eu_E&t=11s
    https://www.youtube.com/watch?v=fi8A4zz1d-s

    展开全文
  • java二进制运算

    2020-08-20 18:57:25
    保留符号位,其余的向左移动N位,整数和负数都是低位补0,相当于乘以2N次方,这种方式用来做2的整数倍乘法运算效率很高。 .>> 保留符号位,其余的向右移动N位,整数高位补0,负数高位补1 . &

    前言

    在讲二进制运算之前,首先得知道原码,反码,补码的概念。举个例子。
    在这里插入图片描述

    二进制运算

    • & 按位逻辑与,都为1则为1,否则为0;
    • | 按位或,都为0则为0,有一个为1则为1;
    • ^ 异或,两个都相同为0,两个不相同为1,11=0,10=1,0^0=0
    • ~ 按位取反,包括符号位;
    • << 保留符号位,其余的向左移动N位,整数和负数都是低位补0,相当于乘以2的N次方,这种方式用来做2的整数倍乘法运算效率很高。
    • .>> 保留符号位,其余的向右移动N位,整数高位补0,负数高位补1
    • . >>> 将符号位也一起移动,高位补0,正数跟>>一样,负数因为符号位是1,移动后的结果可能不是我们预期的。
    • 对于 int 类型的整数移位 a >> b, 当 b>32 时,系统先用 b 对 32 求余(因为 int 是 32 位),得到的结果才是真正移位的位数,例如,a >> 33 和 a >> 1 的结果相同,而 a >> 32 = a;对于 long 类型的整数移位 a >> b, 当 b>64 时,系统先用 b 对 64 求余(因为 long 是 64 位),得到的结果才是真正移位的位数;当进行移位运算时,只要被移位的二进制码没有发生有效位的数字丢失(对于正数而言,通常指被移出去的位全部是 0),不难发现左移 n 位就相当于乘以 2 的 n 次方,右移 n 位则是除以 2 的 n 次方;
    • ~n=-(n+1),3的按位取反 = -4
    • -n&n = 整数n的二进制字符串最后一个1所代表的整数,比如-10 & 10 = 2
    • == n&(n-1) = 整数n的二进制串去掉最后一个1之后 的整数 ==,比如 10 & 9 = 8

    思考题1

    int有32位,有什么方法可以判断这个int中有多少位是1?
    可以直接用Integer.bitCount函数,也可以自定义一个。

        private static int cnt(int value){
            int count = 0;
            while(value != 0){
                value &= (value -1);
                count++;
            }
            return count;
        }
    

    测试代码

        public static void main(String[] args) {
            int a = 10;  //00000000000000000000000000001010
            int b = -10; //11111111111111111111111111110110
            System.out.println("a="+a);
            System.out.println("a的二进制表示:");
            System.out.println(Integer.toBinaryString(a));
            System.out.println("a的二进制表示中1的位数="+Integer.bitCount(a));
            System.out.println("a的二进制表示中1的位数="+cnt(a));
    
            System.out.println("=====================");
            System.out.println("b="+b);
            System.out.println("b的二进制表示:");
            System.out.println(Integer.toBinaryString(b));
            System.out.println("b的二进制表示中1的位数="+Integer.bitCount(b));
            System.out.println("b的二进制表示中1的位数="+cnt(b));
        }
    

    结果输出

    a=10
    a的二进制表示:
    1010
    a的二进制表示中1的位数=2
    a的二进制表示中1的位数=2
    =====================
    b=-10
    b的二进制表示:
    11111111111111111111111111110110
    b的二进制表示中1的位数=30
    b的二进制表示中1的位数=30
    
    Process finished with exit code 0
    

    思考题2

    有a,b两个整数,如何用位运算实现a+b??
    主要考虑用 位异或(也称不进位加) , 按位与 运算来实现。

        public static int add(int a ,int b){
            // 异或运算有一个别名叫做:不进位加法
            // 那么a ^ b就是a和b相加之后,该进位的地方不进位的结果
            // 然后下面考虑哪些地方要进位,自然是a和b里都是1的地方
            // a & b就是a和b里都是1的那些位置,a & b << 1 就是进位之后的结果。
            // 所以:a + b = (a ^ b) + (a & b << 1)
            // 比如:1 + 1 = (1 ^ 1) + (1 & 1 << 1)
            // 可以知道,这个过程是在模拟加法的运算过程,进位不可能
            // 一直持续,所以b最终会变为0。因此重复做上述操作就可以
            // 求得a + b的值。
            while (b != 0) {
                int bujinwei_jia = a ^ b;
                int jinwei = (a & b) << 1;
                a = bujinwei_jia;
                b = jinwei;
            }
            return a;
        }
    
    展开全文
  • 二进制加,减法,23个位运算技巧

    千次阅读 2019-04-06 20:36:22
    二进制加,减法 二进制最高位为1时表示负数,为0时表示正数。 **原码:**一个正数,转换为二进制位就是这个正数的原码。负数的绝对值转换成二进制位然后在高位补1就是这个负数的原码。 举例说明:  int类型的 3 的...
  • 二进制计算

    千次阅读 2021-07-21 05:31:49
    虽然很早就接触了二进制,却一直没有正视这个问题,阅读《计算机科学导论》的时候,基本上是跳过了这一部分,总是以“这么基础的东西,反正工作中基本用不上”的理由给搪塞过去。最近正在阅读《编码》和《程序员的...
  • 二进制  正整数的二进制表示 (假定类型是byte)  正整数的二进制表示与此类似, 只是在十进制中,每个位置可以有10个数字,从0到9,但在二进制中,每个位置只能是0或1。  例如: 0000 1010 ==> 10 负整数...
  • 学习背景:最近在看很多JAVA类的源码,遇到了很多的位运算,所以系统的学习了下有关二进制的知识。 首先,看一下JAVA中的基本数据的字节(Byte)长度和bit长度: 基本数据类型 字节Byte bit byte 1字节 8位 ...
  • 二进制乘法原理

    万次阅读 2015-03-21 21:29:41
    二进制乘法原理:就是左移(进位)8次,每次最高位为1则加进去,8位移完就得出乘积了实际上和我们10进制的乘法是一样的,只不过这里的进制是2罢了比如5×6,转成二进制就是0101×0110 十进制乘法大家都会,公式...
  • )实现2n次方的计算。 数据范围:0≤n≤31 输入描述: 一行输入整数n(0 <= n < 31)。 输出描述: 输出对应的2n次方的结果。 示例1 输入: 2 输出: 4 移位操作符运算规则: (1)右移操作符:...
  • 剑指offer ...求该青蛙跳上一个n级的台阶总共有多少种跳法(先后次序不同算不同的结果)。 class Solution: def jumpFloor(self, number): # write code here if number &lt;=2: return number ...
  • 超有趣的二进制—高效位运算秒懂

    千次阅读 2019-05-20 17:38:23
    运算速度要快于整数运算的,特别是整数乘法,需要10个或者更多个时钟,若果采用移位操作一个或者2个时钟就够了,不过由于我们常采用十进制来进行算术运算,对二进制的位运算不够熟悉,阅读起来会比较耗费精力,...
  • 二进制运算与转换

    2019-10-27 14:35:32
    二进制是逢2进位的进位制,0、1是基本算符。现代的电子计算机技术全部采用的是二进制,因为它只使用0、1两个数字符号,非常简单方便,易于用电子方式实现。计算机内部处理的信息,都是采用二进制数来表示的。二进制...
  • 在java中的二进制运算符有:&lt;&lt;(左移保留符号位), &gt;...在说二进制运算之前,我们先来了解一下原码,反码和补码的概念: 原码:第一位是符号位,0表示正数,1表示负数。其余3...
  • 计算机基础:15、二进制--进制运算基础1、进制概述1.1、进制定义和举例2、常见进制3、二进制运算基础3.1、按权展开法3.2、重复相除法3.3、重复相乘法 1、进制概述 1.1、进制定义和举例 进制的定义 进制是一种计数...
  • 二进制转十进制

    2021-06-19 04:51:47
    64个基数为:"[emailprotected]"注意:本工具只是各种进制计数法的数之间的转换,计算机表示数的方法是进行编码表示,整数有整数的表示方法,浮点数有浮点数的表示方法,所以本工具不能直接把计算机中二进制表示的数...
  • 二进制是如何将加减乘除变换为加法实现的?加法是如何由逻辑运算与、或、异或来实现的?...乘法由于计算机中,所有数值都是用2N次方来表示的:2^n0+2^n1+2^n2+2^n3+2^n4.....因此x*y,(x)*(2^n0+2^n1+2^n2+2^n3+2^n4...
  • 1、什么是位运算?...而位运算就是直接在二进制的数字序列上进行按位与,按位或,按位异或,左移,右移这几种操作。 由于计算机内部本身就是以二进制运算,所以位运算相较算数运算符来说,计算起来就...
  • 表示范围2n次方-1。 有符号数: 原码:用尾数表示真值的绝对值,符号位“0/1”对应“正/负” 若机器字长为n+1位,则尾数占n位。 原码:原码通常用来表示定点小数,用来表示浮点数的尾数。 原码就是用最高位来...
  • 1.将一个二进制数向左位移n位就等于该数乘以2n次方,当乘法运算中的某个数符合这个特点的时候,可以用位移运算代替乘法运算,从而提高效率。 package pp.suanfa; /** * 乘法运算转位移运算 * * @author ...
  • 本来定好每个星期写一遍算法的博客的,可是因为最近赶项目,博客停止更新一段时间了,现在抽空继续...题目:实现一个方法,判断一个正整数是否是2的乘方(比如 16 是 2 的 4 次方,返回 True;18 不是 2 的乘方,返回 F
  • 二进制数的补码及运算2

    千次阅读 2017-02-26 12:04:48
    本章均对整数进行操作,小数情况请先转化为整数并对其符号位。
  • 最近完成了数据结构的课程设计,课程设计的题目选择的是...非对称密码在加密和解密时,是把 加密的数据当作一个大的正整数来处理,这样就涉及到大整数的加、减、、除和指数运算 等,同时,还需要对大整数进行输出...
  • 3 ,即是2乘以2的3次方。由于这里涉及到左移位运算,简单科普下左移位运算,(左移位运算的公式:a<1)例: a<<4 指把a的各进位向左移动4位。如a=00000011(十进制3),左移4位后为00110000(十进制48)。2)...
  • 运算一直视程序执行其中一个重要的环节,而在二进制的运算过程其中,加法运算有时重中之重,他基本上奠定了二进制运算的基础.因此不管是减法还是乘法,都能够由加法运算来取代,只有除法不能取代. 了解了计算机运算的...
  • 起初是CCSP 2019的一道代码优化卡常数的题,有一个数据点就是算斐波那契数列第n某个质数p的的结果。但是因为矩阵快速幂常数太大,卡的非常难受,于是回去想了想有没有简洁优美一点的代码。问题:对输入​ ,计算...
  • 二进制数转换成十进制数:二进制数从右向左每位数乘以2次方(从0开始,从右向左依次+1),然后相加求和即可如:0101转成十进制为:1*20+0*21+1*22+0*23=1+0+4+0=5算法实现:#coding=utf-8b=raw_input("请输入一个...
  • 剑指offer位运算题目汇总: 剑指 Offer II 001; 剑指 Offer II 002; 剑指 Offer II 003; 剑指 Offer II 004; 剑指 Offer II 005; 剑指 Offer 15; 剑指 Offer 16; 剑指 Offer 64; 剑指 Offer 65;
  • 快速幂运算&取模乘法性质的知识点与相关题型精析,与相应实用代码模板。
  • 十进制转二进制例题

    2021-06-09 05:38:08
    )十进制转二进制简单的来讲,就是把一个十进制的数÷2,一直÷,直到不能除了,就像是1÷2,在十进制转二进制的时候,它的答案为0,没有余数就写0,然后把前面的余数全部合并在一起,不是加在一起,如果第一个数是0...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 8,182
精华内容 3,272
关键字:

二进制的模2运算进行2的n次方乘m的运算的乘法怎么做

友情链接: date.rar