系列文章
- [ CodeWar ] - 001:过滤重复字符
- [ CodeWar ] - 002:最大和最小值
- [ CodeWar ] - 003:判断质数
- [ CodeWar ] - 004:处理数组元素
- [ CodeWar ] - 005:用户分组
- [ CodeWar ] - 006:数组比对
- [ CodeWar ] - 007:找不同
- [ CodeWar ] - 008:分割字符串
- [ CodeWar ] - 009:哈希标签生成器
- [ CodeWar ] - 010:大数相加
题目

需求:
- 传入两个整数形式的字符串,需要返回它们的和的字符串
解析
这道题乍一看仿佛一道送分题,不假思索的把代码写下来去跑单测:
const sumStrings = (a, b) => (parseInt(a) + parseInt(b)).toString();
单测结果如下:

其实题目中已经写得很清楚了:
A string representation of an integer will contain no characters besides the ten numerals "0" to "9".
那么显然这里是一个大数相加的问题。
大数相加,说起来好像是一个很复杂的问题,实际上,只要小学上过数学课,应该是有一定思路的:

这里我们只要实现以上算法即可:
- 首先通过
Math.max()获取两个整数中大着的长度 - 然后通过
padStart()将小整数的位数补足- a -
1020301920120 - b -
0000101023019
- a -
- 通过循环计算两个整数每一位相加
- 通过第一个变量记录两个数相加的结果
- 通过第二个变量记录两数相加之后的进位
关键点如上,代码按部就班实现就好:
function sumStrings(a, b) {
const len = Math.max(a.length, b.length);
a = a.padStart(len, 0);
b = b.padStart(len, 0);
let c = 0,
s = 0,
ret = "";
for (let i = len - 1; i >= 0; i--) {
s = parseInt(a[i]) + parseInt(b[i]) + c;
c = Math.floor(s / 10);
ret = (s % 10) + ret;
}
if (c === 1) {
ret = "1" + ret;
}
return ret.replace(/\b(0+)/gi, "");
}
优化
我们总结上述算法可以发现以下特点:
- 进位只会是 0 或 1
那么这里我们就可以借助 Boolean 的特性:
function sumStrings(a, b) {
let arrA = a.split(""),
arrB = b.split(""),
carry = 0,
sum = "";
while (arrA.length || arrB.length || carry) {
carry = carry + (~~arrA.pop() + ~~arrB.pop());
sum = (carry % 10) + sum;
carry = carry > 9;
}
return sum.replace(/^0+/, "");
}
其实核心算法和上面还是一样的。