我正在尝试使用JavaScript来获取数字的第n个根,但是我看不到使用内置Math
对象来实现的方法。我在俯视什么吗?
如果不...
我可以使用具有此功能的数学库吗?
如果不...
自己完成这项工作的最佳算法是什么?
Answers:
使用Math.pow()
请注意,它不能很好地处理负面问题-这是一个讨论,有些代码可以
http://cwestblog.com/2011/05/06/cube-root-an-beyond/
function nthroot(x, n) {
try {
var negate = n % 2 == 1 && x < 0;
if(negate)
x = -x;
var possible = Math.pow(x, 1 / n);
n = Math.pow(possible, n);
if(Math.abs(x - n) < 1 && (x > 0 == n > 0))
return negate ? -possible : possible;
} catch(e){}
}
所述n
的第根x
是一个数r
,使得r
对所述功率的1/n
是x
。
实际上,存在一些子情况:
x
正数和r
偶数时有两种解决方案(符号相反的相同值)。x
正数r
为奇数时有一个正解。x
负数r
为奇数时有一个负数解。x
负数r
为偶数时,没有解决方案。由于Math.pow
不喜欢带有非整数指数的负基数,因此可以使用
function nthRoot(x, n) {
if(x < 0 && n%2 != 1) return NaN; // Not well defined
return (x < 0 ? -1 : 1) * Math.pow(Math.abs(x), 1/n);
}
例子:
nthRoot(+4, 2); // 2 (the positive is chosen, but -2 is a solution too)
nthRoot(+8, 3); // 2 (this is the only solution)
nthRoot(-8, 3); // -2 (this is the only solution)
nthRoot(-4, 2); // NaN (there is no solution)
nthRoot
。由于Math.pow(-4, 1/2)
返回,NaN
并且因为我们只需要Math.abs
负数,所以我们Math.abs
只能将其用于负数和奇数(不确定后者是优化的)。因此,在一行中:let nthRoot = (x, n) => n % 2 === 1 && x < 0 ? -(Math.abs(x) ** (1/n)) : x ** (1/n)
这是一个试图返回虚数的函数。它还首先检查一些常见的事物,例如:获得0或1的平方根,还是获得x的第0个根
function root(x, n){
if(x == 1){
return 1;
}else if(x == 0 && n > 0){
return 0;
}else if(x == 0 && n < 0){
return Infinity;
}else if(n == 1){
return x;
}else if(n == 0 && x > 1){
return Infinity;
}else if(n == 0 && x == 1){
return 1;
}else if(n == 0 && x < 1 && x > -1){
return 0;
}else if(n == 0){
return NaN;
}
var result = false;
var num = x;
var neg = false;
if(num < 0){
//not using Math.abs because I need the function to remember if the number was positive or negative
num = num*-1;
neg = true;
}
if(n == 2){
//better to use square root if we can
result = Math.sqrt(num);
}else if(n == 3){
//better to use cube root if we can
result = Math.cbrt(num);
}else if(n > 3){
//the method Digital Plane suggested
result = Math.pow(num, 1/n);
}else if(n < 0){
//the method Digital Plane suggested
result = Math.pow(num, 1/n);
}
if(neg && n == 2){
//if square root, you can just add the imaginary number "i=√-1" to a string answer
//you should check if the functions return value contains i, before continuing any calculations
result += 'i';
}else if(neg && n % 2 !== 0 && n > 0){
//if the nth root is an odd number, you don't get an imaginary number
//neg*neg=pos, but neg*neg*neg=neg
//so you can simply make an odd nth root of a negative number, a negative number
result = result*-1;
}else if(neg){
//if the nth root is an even number that is not 2, things get more complex
//if someone wants to calculate this further, they can
//i'm just going to stop at *n√-1 (times the nth root of -1)
//you should also check if the functions return value contains * or √, before continuing any calculations
result += '*'+n+√+'-1';
}
return result;
}
好吧,我知道这是一个老问题。但是,基于SwiftNinjaPro的答案,我简化了功能并修复了一些NaN问题。注意:此函数使用了ES6功能,箭头函数和模板字符串以及指数。因此,它可能在较旧的浏览器中不起作用:
Math.numberRoot = (x, n) => {
return (((x > 1 || x < -1) && n == 0) ? Infinity : ((x > 0 || x < 0) && n == 0) ? 1 : (x < 0 && n % 2 == 0) ? `${((x < 0 ? -x : x) ** (1 / n))}${"i"}` : (n == 3 && x < 0) ? -Math.cbrt(-x) : (x < 0) ? -((x < 0 ? -x : x) ** (1 / n)) : (n == 3 && x > 0 ? Math.cbrt(x) : (x < 0 ? -x : x) ** (1 / n)));
};
例:
Math.numberRoot(-64, 3); // Returns -4
示例(虚数结果):
Math.numberRoot(-729, 6); // Returns a string containing "3i".
我已经写了一个算法,但是在此之后需要很多数字的时候它很慢:
https://github.com/am-trouzine/Arithmetic-algorithms-in-different-numeral-systems
NRoot(orginal, nthRoot, base, numbersAfterPoint);
该函数返回一个字符串。
例如
var original = 1000;
var fourthRoot = NRoot(original, 4, 10, 32);
console.log(fourthRoot);
//5.62341325190349080394951039776481