javascript - 乘法持久性代码战挑战
问题描述
我一直在研究 Codewars 的一个 kata,挑战是编写一个函数,持久性,它接受一个正参数 num 并返回它的乘法持久性,这是你必须将 num 中的数字相乘直到你达到的次数一个数字。
例子:
persistence(39) === 3 // because 3*9 = 27, 2*7 = 14, 1*4=4
// and 4 has only one digit
persistence(999) === 4 // because 9*9*9 = 729, 7*2*9 = 126,
// 1*2*6 = 12, and finally 1*2 = 2
persistence(4) === 0 // because 4 is already a one-digit number
在试图弄清楚这一点时,我在网上遇到了一个解决方案(如下所示),在尝试理解它的逻辑之后,我看不出为什么代码不起作用
var count = 0;
function persistence(num) {
if (num.toString().length === 1) {
return count;
}
count++;
var mult = 1;
var splitStr = num.toString().split("");
for (var i = 0; i <= splitStr; i++) {
mult *= parseFloat(splitStr[i])
}
return persistence(parseFloat(mult));
}
任何一位数字的输出都是 0,这是正确的,但是对于任何多位数的数字,持久性总是记录为 1,我似乎无法弄清楚为什么,任何帮助将不胜感激。
解决方案
发布的代码有很多问题。
for (var i = 0; i <= splitStr; i++) {
但是splitStr
是一个数组,而不是一个数字;i <= splitStr
没有意义。它应该检查splitStr.length
而不是splitStr
.
另一个问题是它应该使用i <
,而不是i <=
,否则最终splitStr[i]
将是undefined
。
另一个问题是count
变量是全局的,所以多次调用persistence
会导致结果不准确。根本不需要count
变量。要解决这个问题:
function persistence(num) {
if (num.toString().length === 1) {
return 0;
}
var mult = 1;
var splitStr = num.toString().split("");
for (var i = 0; i < splitStr.length; i++) {
mult *= parseFloat(splitStr[i])
}
return 1 + persistence(parseFloat(mult));
}
console.log(
persistence(999),
persistence(39),
persistence(4)
);
或者,可以完全避免for
循环,并使用更合适的数组方法:
function persistence(num) {
const str = num.toString();
if (str.length === 1) {
return 0;
}
const nextNum = str.split('').reduce((a, b) => a * b, 1);
return 1 + persistence(nextNum);
}
console.log(
persistence(999),
persistence(39),
persistence(4)
);
推荐阅读
- excel - 扫描工作表以查找每个 ID 的缺失项目
- wordpress - Docker for WordPress 慢
- typescript - TypeScript 类型转换
- angular - 为什么在 Angular 中使用 ValueAccessor?
- python-3.x - 使用 Cartopy 代替 Basemap 在 Dash 应用程序中创建地图轨迹
- ios - 由于占位符团队 ID,Flutter ios 失败
- php - 如何在php中生成唯一的推荐码
- java - Spring Boot HttpSecurity 总是 403 被禁止
- javascript - 将 ES6 导入模块与 pkg 一起使用
- .net - Dotfuscator 突然开始重命名公共成员,即使打开了库模式