我正在尝试计算数组中所有重复项的总和。例如:
duplicate([1,1,2,3,3])->应该返回8。
我编写了以下函数,使用JavaScript计算数组中重复项的总和。目前,它返回的数组中的重复项比数组中的重复项少一个。
function duplicate(arr) {
var sum = 0;
arr.sort();
var stack = [];
for(var i = 0; i < arr.length; i++){
if (arr[i] === arr[i+1]) {
stack.push(arr[i])
}
}
return stack;
}
console.log(duplicate([1,2,1,2,2,3,3]))
这将返回[1,2,2,3]
如何获取正确的数组并计算正确的总和?我必须为此使用对象吗?
答案 0 :(得分:4)
为简化逻辑,您可以通过检查数组中的filter
是否等于数组中的indexOf
,lastIndexOf
来消除重复项:
function duplicate(arr) {
const duplicates = arr.filter(elm => arr.indexOf(elm) !== arr.lastIndexOf(elm));
return duplicates.reduce((a, b) => a + b);
}
console.log(duplicate([1,1,2,3,3])); // --> should return 8.
console.log(duplicate([1,2,1,2,2,3,3]));
答案 1 :(得分:1)
问题是您正在将值与数组中的下一个下一个值进行匹配,在已经排序的数组中它可以工作,但不能用于未排序的数组。因此,请尝试先对数组进行排序,然后再运行代码。
编辑: 看起来是在代码中添加了排序,
但是另一个条件=>如果重复的次数超过两次,则应该处理该次数,并且如果需要的话,它仅在堆栈中出现一次。
这将是:console.log(duplicate([1,2,1,2,2,3,3]))
结果为:[1,2,3]
function duplicate(arr) {
var sum = 0;
arr.sort();
var stack = [];
for(var i = 0; i < arr.length; i++){
if (arr[i] === arr[i+1]) {
if(stack.length == 0 || (arr[i] != stack[stack.length-1])){
stack.push(arr[i])
}
}
}
return stack;
}
答案 2 :(得分:1)
最初创建一个对象,其中的键将为整数,其值将为出现的次数。然后,如果出现次数大于1,则将发生次数乘以该次数。
function duplicate(arr) {
let dupVal = 0;
let k = arr.reduce((acc, curr, index) => {
if (acc[curr] === undefined) {
acc[curr] = 1
} else {
acc[curr] += 1;
}
return acc
}, {});
for (let keys in k) {
if (k[keys] > 1) {
dupVal += parseInt(keys, 10) * k[keys]
}
}
return dupVal;
}
console.log(duplicate([1, 2, 1, 2, 2, 3, 3]))
答案 3 :(得分:1)
尝试这个
const arr = [1,1,2,3,3]
let dup = arr.filter((value, index)=>{
// creating a copy of main array
let copyarr = [].concat(arr)
// removing present value
copyarr.splice(index,1)
// after removing present value, if you still
// get the value in copied array that means
// it has duplicates
if(copyarr.indexOf(value)>-1){
return true
}
return false
})
// now add it using reduce
let sum = dup.reduce((acc, value)=> acc+value,0)
console.log(sum)
复制以上代码,然后粘贴到chrome devTool中。您将得到答案。
答案 4 :(得分:0)
您可以使用JS Array.reduce方法以较短的方式满足您的要求
function sumDplicates(arr) {
return arr.reduce(function(tot, val, index, _arr) {
if (_arr.lastIndexOf(val) > index || _arr.indexOf(val) != index)
return tot + val;
return tot
}, 0)
}
console.log(sumDplicates([1, 1, 2, 3, 3]));
console.log(sumDplicates([1, 2, 1, 2, 2, 3, 3]));
答案 5 :(得分:0)
您可以对原始排序方法进行一些修改:
if (arr[i] === arr[i + 1] || arr[i] === arr[i - 1])
也就是说,检查排序数组中的前一个元素或下一个元素是否等于当前元素,以使其有资格重复。
以下解决方案通过filter
和reduce
来实现:
function duplicate(array) {
return array
.sort((a, b) => a - b)
.filter((a, i, arr) => (arr[i] === arr[i + 1] || arr[i] === arr[i - 1]))
.reduce((a, b) => a + b, 0);
}
console.log(duplicate([1, 1, 2, 3, 3]));
console.log(duplicate([1, 2, 1, 2, 3, 3]));
答案 6 :(得分:0)
Array.reduce()和Array.lastIndexOf()只会解决您的问题。
function sum(arr)
{
return arr.reduce(function(sum, item){
return arr.lastIndexOf(item)!==arr.indexOf(item) ? sum+=item : sum;
},0)
}
console.log(sum([1,1,2,3,3]));
console.log(sum([1,2,3,4]));
console.log(sum([1,2,2,3,4]));
console.log(sum([1,1,2,2,3,3,4,4]));
答案 7 :(得分:0)
这里是一种只包含一个Array.reduce
的方法。没有Array.indexOf
或Array.lastIndexOf
。尽管可能不够简洁,但它不会遍历数组以多次查找索引,也不会Array.filter
:
const sumDubs = arr => arr.reduce((r,c) => {
if(r[c]) {
r[c] += 1
r.sum += r[c] > 2 ? (r[c]*c) - ((r[c]-1)*c) : r[c]*c
} else r[c] = 1
return r
}, { sum: 0 }).sum
console.log(sumDubs([1, 1, 2, 3, 3])) // 8
console.log(sumDubs([1, 2, 1, 2, 2, 3, 3])) // 14
console.log(sumDubs([1, 2, 1, 2, 2, 3, 3, 3, 1, 2, 4, 4])) // 28
这个想法是通过Array.reduce
的累加器中的一个属性来跟踪持续的总和,并继续根据重复的数字(更重要的是多少次)来计算总和。
答案 8 :(得分:0)
尽管我对JavaScript不太了解,但是如果我是你,我只会保留一个临时数组,该数组将复制所有重复变量,然后使用该数组求和。 另外,如果您要添加特定数量的数字,则建议将其创建为一个稀疏矩阵中的表 然后在添加过程中引用它。 这种逻辑虽然不节省空间,但很容易实现。