• 不用加减乘除实现两个正整数的加法


    很常见的一道题,网上也有各种各样的解法,备忘一下。

    首先来看十进制整数的加法,123 + 999,将其分为三步来运算:

    (1)对每一位相加,不考虑进位。当有进位时,舍弃。如下:

         123

    +   999

    =   012  

    (2)考虑进位的影响。观察可发现,当个位相加有进位时,实际上少加了10,当百位有进位时,实际上少加了100,依次类推。因此,第二步操作我们得到因为没考虑进位少加的数。当没有进位时为0,当有进位时,舍弃个位,留下十位。比如5 + 6 = 11,舍弃个位,留下十位,为1,即 5 + 6 = 1。对每一位做如此操作:

         123

    +   999

    =   111

    个位: 3 + 9 = 1  少加了10

    十位: 2 + 9 = 1  少加了100

    百位: 1 + 9 = 1  少加了1000

    共少加了 1100,即 111 * 10 = 1110。因为是十进制,所以将进位相加得到的数 111 * 10,即为由于忽略进位少加的数

    (3)将第一步和第二步所得到的数相加:

         012

    + 1100

    = 1112

    得到最后的结果。

    推广到二进制,逢2进1。举例:15 + 11,转化成二进制就是:1111 + 1011,还是按照上面的三个步骤:

    (1)每一位相加,不考虑进位:

         1111

    +   1011

    =   0100

    (2)考虑进位,算出少加的数

           1111

    +     1011

    =     1011

    对应到二进制,从右到左:

    第一位进位:少加了2

    第二位进位:少加了4

    第四位进位:少加了16

    因为是二进制,需要将 1011 * 2,对应到二进制中,就是左移一位,变成 10110

    (3)将第一步和第二步的数相加:

    0100 = 4

    10110 = 22

    和为: 26

    使用二进制加法时:

            0100

    +    10110

    =    11010

    实际上,在上述过程中仍然有进位,继续利用上面的方法。因此,利用二进制实现加法实际上是个循环的过程。

    用程序实现上述步骤:

    第一步中,1 + 1 = 0, 0 + 0 = 0, 1 + 0 = 1, 0 + 1 = 1 ,实际上符合异或的操作(相同为0,不同为1)

    第二步中,1 + 1 = 1, 0 + 0 = 0, 1 + 0 = 0, 0 + 1 = 0, 实际上符合与操作(只有都为1时才为1)

    第三步就是对第一步和第二步的重复。

    代码如下:

    while(cin >> n >> m){
        while(m){
            int sum = n ^ m;
            int temp = (n & m)<<1;
            n = sum;
            m = temp;
        }
        cout << n << endl;    
    }
    View Code
  • 相关阅读:
    算法训练 P1103
    算法训练 表达式计算
    算法训练 表达式计算
    基础练习 时间转换
    基础练习 字符串对比
    Codeforces 527D Clique Problem
    Codeforces 527C Glass Carving
    Codeforces 527B Error Correct System
    Codeforces 527A Glass Carving
    Topcoder SRM 655 DIV1 250 CountryGroupHard
  • 原文地址:https://www.cnblogs.com/acBool/p/4878927.html
Copyright © 2020-2023  润新知