问题
如果相加的两个数位数过多,大于32位(int),大于64位(long),该如果计算?
解决方法
可以用两个字符数组去储存两个大数,然后就是字符相加
具体细节
先拿出草稿,默默的用两个大数,竖式算一遍,然后记住这个过程中过的细节,再转换为代码(也可以先看代码部分,代码部分有详细注释):
- 低位开始相加
转换成代码思维:两个数组保存的数都是低索引保存高位,因此两种方法,一种先把两个数组反转,一种就是从数组最后一位开始计算 - 有进位
在计算的过程中,如果低位相加大于10,需要把结果的余数作为此次结果,除以10的结果作为进位,此进位下次和高位的数相加。 - 两个数组的长度不一致
在计算的过程中是两个数组对应位数的数再加上进位,如果加数已经加完了,那么就是被加数和进位相加就可以了 - 结果需要反转
如果计算的过程中低位相加的结果放在结果数组的低索引中,最后需要把结果反转。
代码实现
#include <iostream>
void reverseStr(char a[], int len_a) {
int mid = len_a / 2;
int i = 0, j = len_a - 1;
char t;
for (int k = 0; k < mid; k++) {
t = a[i];
a[i] = a[j];
a[j] = t;
i++;
j--;
}
}
void strAdd(char output[],char a[], int len_a, char b[], int len_b) {
int i = len_a - 1, j = len_b - 1;
int c = 0;
int sum = 0;
int k = 0;
for (k = 0; k < len_a||k<len_b; k++) {
sum = 0;
if (k < len_a) {
sum += a[i] - '0';
i--;
}
if (k < len_b) {
sum += b[j] - '0';
j--;
}
sum += c;
c = sum / 10;
output[k] = sum % 10 + '0';
printf("temp[%d]=%c ", k, output[k]);
}
if (c == 1) {
output[k] = '1';
output[k + 1] = '\0';
reverseStr(output, k + 1);
}
else {
output[k] = '\0';
reverseStr(output, k);
}
}
int main()
{
char result[1000];
char str1[100] = { '3','5','8','7','9','1'};
char str2[100] = { '5','9','9','6','5','5','7'};
strAdd(result,str1, 6, str2,7);
char* str3 = result;
while (*str3 != '\0') {
printf("%c", *str3);
str3++;
}
printf("\n");
return 0;
}
运行结果
调式注意的地方
1, 代码中i,j,k的数值变化是否正确 2. 加数和被加数都加完了,是否考虑了最后一次的进位 3. 在相加的时候是否转成了int型,结果是否转回成字符型
代码实现技巧
- 每次不是加数+被加数+进位一起加,而是判断,如果加数没有加完,加上;如果被加数没有加完,加上;
- 加数和被加数刚开始没有反转,而是从最后一位开始
总结
大数加法,大数减法,大数乘法,大数除法这些都没有用到什么特别的算法或者想不到的技巧,更考验算法的基本功。做算法千万不能看一眼,感觉会了就可以了;需要自己练,敲代码,调式出来了,还有以后碰到这个可以很快的写出来,这样就是会了。
写在最后的话
这段时间碰到的那些人那些事:
1. 某天打滴滴顺风车,同行的是一位做医疗器械公司的员工。同行者聊了起来: 说她们公司之前欠几个亿,这段时间由于呼吸机急需,她们公司赚了几个亿,然后上市了,员工福利待遇也提高了,越说越嗨。
2. 某天打滴滴顺丰车,顺风车司机是做外贸(出口服装)公司的员工。聊了起来:现在她们每个月可以拿到三千多的基本工资,五险一金以最少的标准,公司帮忙交。公司鼓励她们出去赚赚钱,然后她就开起了滴滴顺风车;然后回忆起她们公司以前的光景。
每次静静的听着,听着她们的故事,仿佛跟着她们的思绪快速的走了一遍她们的生活,感受着她们的开心与失落~~
也许人生无常,过好每一天,做好每一天想做的事,吃好想吃的食物,甚好~~
|