首页 > 解决方案 > 如何在“Scala”中按键减少 [不在 Spark 中]

问题描述

我正在尝试在 Scala 中减少 ByKeys,是否有任何方法可以根据 Scala 中的键来减少值。[我知道我们可以通过 spark 中的 reduceByKey 方法来做,但是我们如何在 Scala 中做同样的事情?]

输入数据是:

val File = Source.fromFile("C:/Users/svk12/git/data/retail_db/order_items/part-00000")
                 .getLines()
                 .toList

 val map = File.map(x => x.split(","))
               .map(x => (x(1),x(4)))

  map.take(10).foreach(println)

在上述步骤之后,我得到的结果为:

(2,250.0)
(2,129.99)
(4,49.98)
(4,299.95)
(4,150.0)
(4,199.92)
(5,299.98)
(5,299.95)

预期结果 :

(2,379.99)
(5,499.93)
.......

标签: scalahigher-order-functions

解决方案


开始Scala 2.13,您可以使用groupMapReduce(顾名思义)等效于 agroupBy后跟mapValuesreduce步骤的方法:

io.Source.fromFile("file.txt")
  .getLines.to(LazyList)
  .map(_.split(','))
  .groupMapReduce(_(1))(_(4).toDouble)(_ + _)

groupMapReduce舞台:

  • groups 由它们的第二个元素 ( ) 拆分的数组(MapReduce_(1)的组部分)

  • maps 每个组中的每个数组出现到其第 4 个元素并将其转换为Double( _(4).toDouble)(映射组Map Reduce 的一部分)

  • reduce通过对每个组 ( _ + _) 中的 s 值求和(减少 groupMap Reduce的一部分)。

这是可以通过以下方式翻译的一次性版本

seq.groupBy(_(1)).mapValues(_.map(_(4).toDouble).reduce(_ + _))

还要注意从IteratortoLazyList的转换,以便使用提供的集合groupMapReduce(我们不使用 a ,Stream因为 start是推荐的 s 替换)。Scala 2.13LazyListStream


推荐阅读