javascript 返回范围内所有数字的总和
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/30036206/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
return sum all numbers in a range
提问by jyoon006
function sumAll(arr) {
var list = [];
for (var i = arr[0]; i <= arr[1]; i++) {
list.push(i);
}
var total = list.reduce(function(a, b) {
return a + b;
});
return total;
}
sumAll([10, 5]);
//sumAll([1, 4]); //returns 10
//sumAll([5, 10]); //returns 45
//sumAll([4, 1]);
I need to sum every number in between the given arguments. For sumAll([1, 4])
and sumAll([5, 10])
. The code will pass because it creates all numbers in between the two arguments and adding it. However, for sumAll([10, 5])
and sumAll([4, 1])
, because the greater number is first argument, I believe it does not run var list. I tried using .sort()
method in between so that the numbers are sorted but can't get it to work. How can I use Math.min()
and Math.max()
for this code to work?
我需要对给定参数之间的每个数字求和。对于sumAll([1, 4])
和sumAll([5, 10])
。代码会通过,因为它创建了两个参数之间的所有数字并将其相加。但是,对于sumAll([10, 5])
and sumAll([4, 1])
,因为较大的数字是第一个参数,所以我相信它不会运行 var list。我尝试.sort()
在两者之间使用方法,以便对数字进行排序,但无法使其正常工作。如何使用Math.min()
和Math.max()
此代码工作?
回答by jcarpenter2
Easiest way is to use the mathematical formula
最简单的方法是使用数学公式
1+2+...+n = n(n+1)/2
Here you want the sum,
在这里你想要总和,
m+(m+1)+...+n
where m=arr[0]
and n=arr[1]
. This is equal to the difference
哪里m=arr[0]
和n=arr[1]
。这等于差
(1+2+...+n) - (1+2+...+(m-1))
which substituting the above formula twice is equal to
将上述公式代入两次等于
n(n+1)/2 - (m-1)m/2
So the correct code is
所以正确的代码是
function sumAll(arr) {
var min = arr[0];
var max = arr[1];
return (max*(max+1) - (min-1)*min)) / 2;
}
Original answer (do not use - left for posterity):
原始答案(请勿使用 - 留给后代):
Here's how I'd use Math.min
and Math.max
to do this:
这是我如何使用Math.min
和Math.max
执行此操作的方法:
function sumAll(arr) {
var list = [];
var lower = Math.min(arr[0], arr[1]);
var upper = Math.max(arr[0], arr[1]);
for (var i = lower; i <= upper; i++) {
list.push(i);
}
var total = list.reduce(function(a, b) {
return a + b;
});
return total;
}
Someone else posted code using arr[0] < arr[0] ? arr[0] : arr[1]
; IMO the Math.min
and Math.max
functions make for more readable code than the ? : operator.
其他人使用arr[0] < arr[0] ? arr[0] : arr[1]
;发布了代码 IMOMath.min
和Math.max
函数使代码比 ? : 操作员。
Also, two more cents: I believe it would be simpler to not make a var list
at all; instead say var total = 0
and increment it. Like this:
另外,还有两美分:我相信根本不做会更简单var list
;而是说var total = 0
并增加它。像这样:
function sumAll(arr) {
var lower = Math.min(arr[0], arr[1]);
var upper = Math.max(arr[0], arr[1]);
var total = 0;
for (var i = lower; i <= upper; i++) {
total += i;
}
return total;
}
回答by Nigel
This is one of those times where mathematical equations come in handy. Check out this code:
这是数学方程派上用场的时代之一。看看这个代码:
function sumAll(arr) {
max = Math.max(arr[0], arr[1]);
min = Math.min(arr[0], arr[1]);
return (max * (max + 1) / 2) - ((min - 1) * min / 2);
}
Quite simple logic, right? :)
很简单的逻辑吧?:)
回答by Bertrand KHE
function sumAll(arr) {
var first = arr[0] > arr[1] ? arr[1] : arr[0],
last = arr[0] > arr[1] ? arr[0] : arr[1];
sum = 0;
for (var i = first; i <= last; i++) {
sum += i;
}
return sum;
}
回答by sugongqing
function sumAll(arr) {
var max = Math.max.apply(null, arr);
var min = Math.min.apply(null, arr);
var arr2 = [];
for (var i = min; i <= max; i++) {
arr2.push(i);
}
return arr2.reduce(function(sum, item) {
sum += item;
return sum;
}, 0);
}
console.log( sumAll([1, 4]) )
回答by Damian Kacprzak
With the addition of ES6
随着 ES6 的加入
function sumAll(arr) {
const min = Math.min(...arr)
const max = Math.max(...arr)
let list = []
for(let i = min;i <= max; i++){
list.push(i)
}
return list.reduce((prev, next) => prev + next);
}
sumAll([1, 4]);
回答by guesshwu
Using the while loop:
使用while循环:
function sumAll(arr) {
var i = Math.min(...arr)
var total = 0
while(i <= Math.max(...arr)) {
total += i
i++
}
return total;
}
sumAll([1, 4];
回答by Juan Carrey
function sumAll(arr) {
const rangeStart = Math.min(arr[0], arr[1]);
const rangeEnd = Math.max(arr[0], arr[1]);
const numberOfDigits = rangeEnd - rangeStart + 1;
return (rangeEnd + rangeStart) * numberOfDigits / 2;
}
It is kind of: https://betterexplained.com/articles/techniques-for-adding-the-numbers-1-to-100/
这是一种:https: //betterexplained.com/articles/techniques-for-adding-the-numbers-1-to-100/
But not starting always at 1 but at "rangeStart" and the numberOfDigits is not always rangeEnd, but the idea is the same.
但并不总是从 1 开始,而是从“rangeStart”开始,并且 numberOfDigits 并不总是 rangeEnd,但想法是一样的。
回答by Ashutosh Jha
Between α and β, there are β?α+1 numbers. We need
在α和β之间,有β?α+1个数字。我们需要
S=α+(α+1)+?+β=β+(β?1)+?+α
Adding vertically, we have
垂直相加,我们有
2S=(β?α+1)(α+β)
Hence
因此
S=(β?α+1)(α+β)2
This "reverse and add" technique is due to Gauss and can be used to sum any arithmetic progression as well.
这种“反向加法”技术源于高斯,也可用于对任何算术级数求和。
function sumAll(arr) {
let alpha = Math.min(...arr);
let beta= Math.max(...arr);
return ((beta - alpha + 1)*(alpha + beta))/2;
}
回答by Luigi Derson
What about this one? following the Gauss Formula:
这个如何?遵循高斯公式:
function sumAll(arr) {
return arr.reduce((a,b) => (a+b)*(Math.abs(a-b) + 1) / 2)
}
console.log(sumAll([1,4])); //10
console.log(sumAll([5,10])); //45
console.log(sumAll([10,5])); //45
回答by WesleyAC
Something like this O(1) approach is probably the best way to go:
像这样的 O(1) 方法可能是最好的方法:
function SumRange(a, b) {
if (a > b) return 0;
var sum = (b * ++b) / 2;
return a > 1 ? sum - SumRange(0, --a) : sum;
}
var array = [1, 100];
console.log(SumRange(array[0], array[1]));//5050
console.log(SumRange(10, 100));//5005
The idea is to silo off the SumRange equation so that it can be the single source of truth that can be called from anywhere. Reusability is always a plus.
这个想法是将 SumRange 方程孤立起来,这样它就可以成为可以从任何地方调用的单一事实来源。可重用性总是一个优点。