CoffeeScript减少跳过相同的值

时间:2015-09-18 00:47:29

标签: coffeescript

我正在使用CoffeeScript将列表中的元素聚合到组合对象中。但是,当我有两个相同的值时,其中一个值将被忽略。不是跳过其中一个值,而是如何得到它们的总和?

metals = [
  { metal: 'silver', amount: 10 }
  { metal: 'gold',   amount: 16 }
  { metal: 'iron',   amount: 17 }
  { metal: 'iron',   amount:  3 }
]

reduction = metals.reduce (x, y) ->
  x[y.metal]= y.amount
  x
, {}

console.log reduction
# => { silver: 10, gold: 16, iron: 3 }, but I  would like to get iron: 20    

这是一个帮助解决问题{jsfiddle} {/ 3}}

1 个答案:

答案 0 :(得分:2)

如果您希望reduce总结一下,那么您必须这样说:

reduction = metals.reduce (x, y) ->
  x[y.metal] = (x[y.metal] ? 0) + y.amount
  x
, { }

x[y.metal] ? 0只是说"如果x[y.metal]已定义,则使用它,否则使用0"。你也可以说:

reduction = metals.reduce (x, y) ->
  x[y.metal] = (x[y.metal] || 0) + y.amount
  x
, { }

因为您不关心x[y.metal]的{​​false}值,例如0''falsenull或{{1 }};在你的情况下,你可以将所有这些转换为零。

您还可以更明确地了解自己在做什么:

undefined

如果reduction = metals.reduce (x, y) -> x[y.metal] = 0 if(y.metal !of x) x[y.metal] += y.amount x , {} 已经没有x[y.metal] = 0 if(y.metal !of x)属性,x[y.metal]只会将x初始化为零。如果您不喜欢y.metal

,也可以使用unless
!of

请记住,所有reduction = metals.reduce (x, y) -> x[y.metal] = 0 unless(y.metal of x) x[y.metal] += y.amount x , {} 都会运行您提供的功能,并将功能的输出反馈给自己:

reduce

只是:

[1,2,3].reduce f, i

f(f(f(i, 1), 2), 3) 函数对其输入的作用以及它返回的内容取决于您。