Javascript 如何对对象的值求和并将其推送到数组中

Javascript 如何对对象的值求和并将其推送到数组中,javascript,arrays,object,d3.js,Javascript,Arrays,Object,D3.js,我有一个对象数组,它是动态的,取决于表中行的选择。例如: var obj = [ { name: "test1", totalCosts: 45560, actualTotalCosts: 652112, riskCosts: 65442 }, { name: "test2", totalCosts: 3434, actualTotalCosts: 25252, riskCosts: 34234 }, { name

我有一个对象数组,它是动态的,取决于表中行的选择。例如:

var obj = [
            { name: "test1",  totalCosts: 45560, actualTotalCosts: 652112, riskCosts: 65442 },
            { name: "test2",  totalCosts: 3434,  actualTotalCosts: 25252,   riskCosts: 34234 },
            { name: "test3",  totalCosts: 23123, actualTotalCosts: 23242,  riskCosts: 0 },
        ];
生成此数组后,我想调用一个函数,该函数在该数组中再推一行,将其命名为total,并对所有相关值求和,如下所示:

{名称:总计,总成本:72117,实际总成本:700606,风险成本:99676}

obj[0]。totalCosts+obj[1]。totalCosts+obj[2]。totalCosts=obj[3]。totalCosts

我试着用我有限的知识编写一个函数,但该函数不是将所有三个对象的值求和,而是将整个对象求和为一

            function sum1( obj ) {
            var result1 = [];
            for (var i = 0; i < obj.length; i++) {
                var sum = 0, arr = [];
                for (var key in obj[i]) {
                    if (key != 'name') {
                        sum += obj[i][key];
                        arr.push(sum[key]);
                    }

                }
                result1.push(arr);
                return result1;
            }
        }
请提供一个函数,该函数可以对所有对象求和,并返回包含总数的数组。我也尝试过使用d3.sum,但没有成功。

注意:重要的是要认识到,您所调用的var obj实际上是一个数组

也就是说,您可以迭代数组并执行以下操作:

function sumAll(arr) {

  // Create variables for the costs we're tracking
  var totalCosts = 0;
  var actualTotalCosts = 0;
  var riskCosts = 0;

  arr.forEach(function(elem) {
    // At each iteration of our loop, increase the appropriate variables by their appropriate values
    if (elem.hasOwnProperty('totalCosts')) {
      totalCosts += elem.totalCosts;
    }
    if (elem.hasOwnProperty('actualTotalCosts')) {
    actualTotalCosts += elem.actualTotalCosts;
    }
    if (elem.hasOwnProperty('riskCosts')) {
      riskCosts += elem.riskCosts
    }
  });

  // Return an object with the information we'd like to have
  return {
    name: 'total',
    totalCosts: totalCosts,
    actualTotalCosts: actualTotalCosts,
    riskCosts: riskCosts
  }
}
从您的代码:

var obj = [
            { name: "test1",  totalCosts: 45560, actualTotalCosts: 652112, riskCosts: 65442 },
            { name: "test2",  totalCosts: 3434,  actualTotalCosts: 25252,   riskCosts: 34234 },
            { name: "test3",  totalCosts: 23123, actualTotalCosts: 23242,  riskCosts: 0 },
        ];
调用我的函数:

sumAll(obj) // {name: "total", totalCosts: 72117, actualTotalCosts: 700606, riskCosts: 99676}
注意:重要的是要认识到,您所调用的var obj实际上是一个数组

也就是说,您可以迭代数组并执行以下操作:

function sumAll(arr) {

  // Create variables for the costs we're tracking
  var totalCosts = 0;
  var actualTotalCosts = 0;
  var riskCosts = 0;

  arr.forEach(function(elem) {
    // At each iteration of our loop, increase the appropriate variables by their appropriate values
    if (elem.hasOwnProperty('totalCosts')) {
      totalCosts += elem.totalCosts;
    }
    if (elem.hasOwnProperty('actualTotalCosts')) {
    actualTotalCosts += elem.actualTotalCosts;
    }
    if (elem.hasOwnProperty('riskCosts')) {
      riskCosts += elem.riskCosts
    }
  });

  // Return an object with the information we'd like to have
  return {
    name: 'total',
    totalCosts: totalCosts,
    actualTotalCosts: actualTotalCosts,
    riskCosts: riskCosts
  }
}
从您的代码:

var obj = [
            { name: "test1",  totalCosts: 45560, actualTotalCosts: 652112, riskCosts: 65442 },
            { name: "test2",  totalCosts: 3434,  actualTotalCosts: 25252,   riskCosts: 34234 },
            { name: "test3",  totalCosts: 23123, actualTotalCosts: 23242,  riskCosts: 0 },
        ];
调用我的函数:

sumAll(obj) // {name: "total", totalCosts: 72117, actualTotalCosts: 700606, riskCosts: 99676}

你可以在d3的帮助下采用函数法。求和

  obj.push(d3.keys(obj[0])                //get the keys from obj[0]
    .reduce(function(sumRow, sumCol) {    //construct a summary row
      var isNum = !isNaN(obj[0][sumCol])  //only sum numeric fields
      return (sumRow[sumCol] = (isNum ? d3.sum(obj, function(row) {
        return row[sumCol]                //accessor for the column for  d3.sum
      }) : "All"), sumRow)                //append the sum col to the sum row object
    },{}));                               //initial value for reduce is {}
工作示例 作用{ var obj=[{ 名称:test1, 名称2:type1, 总成本:45560, 实际总成本:652112, 风险成本:65442 }, { 名称:test2, 名称2:type2, 总成本:3434, 实际总成本:25252, 风险成本:34234 }, { 名称:test3, 名称2:type3, 总费用:23123, 实际总成本:23242, 风险成本:0 }]; obj.pushd3.keysobj[0] .还原功能Sumrow,sumCol{ 变量isNum=!isNaNobj[0][sumCol] return sumRow[sumCol]=isNum?d3.sumobj,functionrow{ 返回行[sumCol] }:全部,萨姆罗 }, {}; d3.selectresult.textJSON.stringifyobj }
你可以在d3的帮助下采用函数法。求和

  obj.push(d3.keys(obj[0])                //get the keys from obj[0]
    .reduce(function(sumRow, sumCol) {    //construct a summary row
      var isNum = !isNaN(obj[0][sumCol])  //only sum numeric fields
      return (sumRow[sumCol] = (isNum ? d3.sum(obj, function(row) {
        return row[sumCol]                //accessor for the column for  d3.sum
      }) : "All"), sumRow)                //append the sum col to the sum row object
    },{}));                               //initial value for reduce is {}
工作示例 作用{ var obj=[{ 名称:test1, 名称2:type1, 总成本:45560, 实际总成本:652112, 风险成本:65442 }, { 名称:test2, 名称2:type2, 总成本:3434, 实际总成本:25252, 风险成本:34234 }, { 名称:test3, 名称2:type3, 总费用:23123, 实际总成本:23242, 风险成本:0 }]; obj.pushd3.keysobj[0] .还原功能Sumrow,sumCol{ 变量isNum=!isNaNobj[0][sumCol] return sumRow[sumCol]=isNum?d3.sumobj,functionrow{ 返回行[sumCol] }:全部,萨姆罗 }, {}; d3.selectresult.textJSON.stringifyobj }
您不需要在foreach循环中使用Objects hasOwnProperty吗?我知道你在循环一个数组,但是你在检查Obects属性?你是对的,我应该在那里检查边缘情况。我马上更新我的答案。hasOwnProperty应该是字符串,而不是绝对是数字的可变totalCosts。不起作用,totalCosts和actualCosts是动态的,用户可以随时选择不同的costs值。您不需要在foreach循环中使用对象hasOwnProperty吗?我知道你在循环一个数组,但是你在检查Obects属性?你是对的,我应该在那里检查边缘情况。我会马上更新我的答案。hasOwnProperty应该采用字符串,而不是绝对是数字的可变totalCosts。不起作用,totalCosts和actualCosts是动态的,用户可以随时选择不同的成本值。回答不错!您可能希望将列的名称从“全部”更改为“总计”,以完全符合OP的要求。@altocumulus干杯,伙计。。。是的,也许你是对的。我确实考虑过这一点,但之所以选择,是因为我正在把它概括成一个具有任意归纳操作和排除规则的对象。为我工作,谢谢完美的答案,我已经在我的页面中有了D3作为一个角度D3应用,好的。对我来说,这只是另一个例子,表明在d3中很少会找不到您需要的代码。它总是值得到处看看;ECMA5函数式编程风格是实现这一点的强大工具。回答不错!您可能希望将列的名称从“全部”更改为“总计”,以完全符合OP的要求。@altocumulus干杯,伙计。。。是的,也许你是对的。我确实考虑过这一点,但之所以选择,是因为我正在把它概括成一个具有任意归纳操作和排除规则的对象。为我工作,谢谢完美的答案,我已经在我的页面中有了D3作为一个角度D3应用,好的。对我来说,这只是另一个例子,表明在d3中很少会找不到您需要的代码。它总是值得到处看看;以及ECMA5函数式编程风格 是实现这一目标的强大工具。