Spark Mapvalues与地图

时间:2016-05-11 05:28:48

标签: scala apache-spark

所以我在另一个用户问的stackoverflow上看到了这个问题,我试图自己编写代码,因为我正在尝试实践scala和spark:

问题是要从列表中找到每个键的平均值:

假设列表为:( (1,1), (1,3), (2,4), (2,3), (3,1) )

代码是:

val result = input.combineByKey(
(v) => (v, 1),
(acc: (Int, Int), v) => (acc._1 + v, acc._2 + 1),
(acc1: (Int, Int), acc2: (Int, Int)) => (acc1._1 + acc2._1, acc1._2 + acc2._2)).
map{ case (key, value) => (key, value._1 / value._2.toFloat) }  
result.collectAsMap().map(println(_))

所以基本上上面的代码会创建一个[Int, (Int, Int)]类型的RDD,其中第一个Int是键,值是(Int, Int),其中第一个Int是使用相同的键添加所有值,第二个Int是键出现的次数。

我理解发生了什么,但出于某种原因,当我重写这样的代码时:

val result = input.combineByKey(
(v) => (v, 1),
(acc: (Int, Int), v) => (acc._1 + v, acc._2 + 1),
(acc1: (Int, Int), acc2: (Int, Int)) => (acc1._1 + acc2._1, acc1._2 + acc2._2)).
mapValues(value: (Int, Int) => (value._1 / value._2))
result.collectAsMap().map(println(_))

当我使用mapValues而非使用case关键字的地图时,代码无法正常工作。它会显示错误error: not found: type /使用带有case和mapValues的地图有什么不同。因为我认为映射值只取值(在这种情况下是(Int,Int))并返回一个新值,键值保持相同。

2 个答案:

答案 0 :(得分:1)

val result = input.combineByKey(
(v) => (v, 1),
(acc: (Int, Int), v) => (acc._1 + v, acc._2 + 1),
(acc1: (Int, Int), acc2: (Int, Int)) => (acc1._1 + acc2._1, acc1._2 + acc2._2)).
mapValues(value => (value._1 / value._2))
result.collectAsMap().map(println(_))

答案 1 :(得分:0)

没关系,我发现了一篇很好的文章来解决我的问题:http://danielwestheide.com/blog/2012/12/12/the-neophytes-guide-to-scala-part-4-pattern-matching-anonymous-functions.html

如果其他人有相同的问题可以解释它!