Spark中的加权平均值

时间:2015-12-17 01:26:09

标签: scala apache-spark

我有两个RDD,第一个我打电话给userVisits看起来像这样:

((123, someurl,Mon Nov 04 00:00:00 PST 2013),11.0)

,第二个是allVisits:

((someurl,Mon Nov 04 00:00:00 PST 2013),1122.0)

我可以userVisits.reduceByKey(_+_)可以获得该用户的访问次数。我可以做所有的访问,并得到相同的。我想要做的是获得用户的加权平均值,将用户访问次数除以当天的总访问次数。我需要在allVisits中查找一个值,其中包含用户访问中的关键元组的一部分。我猜这可以用这样的地图来完成:

userVisits.reduceByKey(_+_).map( item => item._2 / allVisits.get(item._1))

我知道 allVisits.get(key)并不存在,但我怎么能做到这样的事情?

另一种方法是从allVisits获取密钥并从userVisits映射每个密钥然后加入两个密钥,但这似乎效率低下。

1 个答案:

答案 0 :(得分:2)

我在这里看到的唯一通用选项是join

val userVisitsAgg = userVisits.reduceByKey(_ + _)
val allVisitsAgg = allVisits.reduceByKey(_ + _)

userVisitsAgg.map{case ((id, url, date), sum) => ((url, date), (id, sum))}
  .join(allVisitsAgg)
  .map{case ((url, date), ((id, userSum), (urlSum))) => 
    ((id, url, date), userSum / urlSum)}

如果allVisitsAgg足够小,无法播放,您可以将上述内容简化为以下内容:

val allVisitsAggBD = sc.broadcast(allVisitsAgg.collectAsMap)
userVisitsAgg.map{case ((id, url, date), sum) =>
  ((id, url), sum / allVisitsAggBD.value((url, date)))
}