You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何用D3.js同时实现按Zone分组、汇总统计并保留原始数据?

解决方案:结合分组、汇总与保留原始数据

你已经离目标很近啦!其实不用手动合并两次分组结果,不管是用d3.js还是原生JavaScript,都能在一次遍历/分组过程中同时完成汇总统计和保留原始数据,性能完全不用担心。

方法一:使用d3.js实现

d3.nest的rollup函数里不仅可以计算汇总值,还能直接把当前组的原始数据存下来,最后再调整一下结构就能得到你想要的结果:

var test = [ 
  { "Name":"One Name", "Zip":"75001", "Zone":"A", "qty":60 }, 
  { "Name":"Two Name", "Zip":"75003", "Zone":"A", "qty":40 }, 
  { "Name":"Three Name", "Zip":"75009", "Zone":"B", "qty":20 } 
];

const groupedResult = d3.nest()
  .key(function(d) { return d.Zone; })
  .rollup(function(values) {
    // 在rollup里同时计算汇总值并保留原始数据
    return {
      qtySum: d3.sum(values, function(d) { return d.qty; }),
      cnt: values.length,
      values: values // 直接存入当前组的原始数据数组
    };
  })
  .entries(test)
  // 把d3.nest返回的key/value结构转换成你需要的格式
  .map(function(group) {
    return {
      Zone: group.key,
      ...group.value
    };
  });

console.log(groupedResult);

这个方法的优势是复用了你已经熟悉的d3.nest分组逻辑,所有操作都在分组流程中完成,不会有额外的性能开销。

方法二:原生JavaScript实现(无需依赖库)

如果不想依赖d3.js,用原生JS的reduce方法也能高效完成需求,只需要遍历一次原始数组:

var test = [ 
  { "Name":"One Name", "Zip":"75001", "Zone":"A", "qty":60 }, 
  { "Name":"Two Name", "Zip":"75003", "Zone":"A", "qty":40 }, 
  { "Name":"Three Name", "Zip":"75009", "Zone":"B", "qty":20 } 
];

const groupedResult = Object.values(test.reduce(function(acc, item) {
  const zone = item.Zone;
  // 如果当前区域还没在累加器里,初始化分组结构
  if (!acc[zone]) {
    acc[zone] = {
      Zone: zone,
      qtySum: 0,
      cnt: 0,
      values: []
    };
  }
  // 更新汇总值和原始数据
  acc[zone].qtySum += item.qty;
  acc[zone].cnt += 1;
  acc[zone].values.push(item);
  return acc;
}, {}));

console.log(groupedResult);

两种方法最终输出的结果都和你期望的完全一致,而且都是O(n)的时间复杂度,处理大数据量也很高效。

内容的提问来源于stack exchange,提问作者B-Ray

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.28 07:30:34