假设我们有一个分数 2/4
,可以将其化简为 1/2
。
是否有一种 JavaScript 函数可以进行化简操作?
假设我们有一个分数 2/4
,可以将其化简为 1/2
。
是否有一种 JavaScript 函数可以进行化简操作?
// Reduce a fraction by finding the Greatest Common Divisor and dividing by it.
function reduce(numerator,denominator){
var gcd = function gcd(a,b){
return b ? gcd(b, a%b) : a;
};
gcd = gcd(numerator,denominator);
return [numerator/gcd, denominator/gcd];
}
reduce(2,4);
// [1,2]
reduce(13427,3413358);
// [463,117702]
var FractionReduce = (function(){
//Euclid's Algorithm
var getGCD = function(n, d){
var numerator = (n<d)?n:d;
var denominator = (n<d)?d:n;
var remainder = numerator;
var lastRemainder = numerator;
while (true){
lastRemainder = remainder;
remainder = denominator % numerator;
if (remainder === 0){
break;
}
denominator = numerator;
numerator = remainder;
}
if(lastRemainder){
return lastRemainder;
}
};
var reduce = function(n, d){
var gcd = getGCD(n, d);
return [n/gcd, d/gcd];
};
return {
getGCD:getGCD,
reduce:reduce
};
}());
alert(FractionReduce.reduce(3413358, 13427));
我知道这是一个旧帖子,但是我将被采纳的答案转换成了循环解决方案,而不是递归函数。这样会更加节省内存,并且可能会更快(无需进行内存堆栈操作和执行调用)。
function reduce(numerator, denominator) {
var a = numerator;
var b = denominator;
var c;
while (b) {
c = a % b; a = b; b = c;
}
return [numerator / a, denominator / a];
}
内存占用仅为5个Number结构和一个简单的循环。
var a = Ratio(2,4);
a.toString() == "2/4";
a.simplify().toString() == "1/2"; // reduce() returns a clone of the Ratio()
a.toString() == "2/4"; // Ratio functions are non-destructive.
这里是一个使用 ECMAScript 6 reduce 的递归函数。只要余数不太小,它就适用于大多数分数。0 已被重新定义,以使其适用于像 [1.2、2.4、12、24] 这样的数组。我在 Chrome 和 IE Edge 中进行了测试,因此它在其他浏览器或升级中可能会有所不同。所以它应该可以处理浮点数数组。
Array.prototype.gcd = function () {
if (this.length === 0)
return null;
return this.reduce((prev, curr) => {
if (curr <= 1.00000000001e-12)
return prev
else
return [curr, prev % curr].gcd();
});
}
var reducedValueGCD = [1.2, 2.4, 12, 24, 240].gcd();
搜索 MDN 的 reduce 或者更多信息 在这里。
function reduce([numerator, denominator]){
for (let i = numerator; i > 0; i--) {
if(!(numerator % i) && !(denominator % i)){
return [(numerator / i), (denominator / i)];
}
}
}
function reduceFraction(string){
return reduce(string.split('/').map(n => +n)).join('/');
}
one = '2/4';
two = '20/200';
three = '330/2050';
console.log('2/4 reduced to', reduceFraction(one));
console.log('20/200 reduced to', reduceFraction(two));
console.log('330/2050 reduced to', reduceFraction(three));
除了Jan之外,我会更改他的函数为:
function reduce(numerator,denominator){
var roundNr = 0
if(numerator >= denominator) {
roundNr = Math.floor(numerator / denominator);
numerator -= (roundNr * denominator);
}
var gcd = function gcd(a,b){
return b ? gcd(b, a%b) : a;
};
gcd = gcd(numerator,denominator);
return {roundNr: roundNr, numerator: numerator/gcd, denominator: denominator/gcd}; }
当分子>=分母时,这也将返回roundnumber。
gcd
函数。我唯一建议的更改是对于'NaN'进行某种形式的输入检查,因为'gcd(NaN,1)'会产生'1',而我希望得到的是'NaN'或错误提示。 - zzzzBovif (isNaN(numerator) || isNaN(denominator)) return NaN;
添加为第一行。 - Phrogzreduce(Math.round(.25 * 4), 4))
这将使小(估计)值固定在您给出的最大分母上。 - dmarr