Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/scala/16.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Scala groupBy+;mapValues+;映射回初始格式。有更好的办法吗_Scala - Fatal编程技术网

Scala groupBy+;mapValues+;映射回初始格式。有更好的办法吗

Scala groupBy+;mapValues+;映射回初始格式。有更好的办法吗,scala,Scala,在我正在进行的项目中,我经常发现自己在做以下模式 给定一个案例类X(a:a,b:b,c:c,d:Int),以及此类X的xs:list[X]的列表, 我要做的数据库等价于按a、b、c分组,同时按d求和,返回类型为List[X] 我通常最后做的是 xs.groupBy{case X(a,b,c,d) => (a,b,c)).mapValues(_.sum).map(((a,b,c),d)) => X(a,b,c,d)) 我的问题是,在scala标准库或Scalaz中有没有更好/更清晰/

在我正在进行的项目中,我经常发现自己在做以下模式

给定一个案例类X(a:a,b:b,c:c,d:Int),以及此类X的xs:list[X]的列表, 我要做的数据库等价于按a、b、c分组,同时按d求和,返回类型为List[X]

我通常最后做的是

xs.groupBy{case X(a,b,c,d) => (a,b,c)).mapValues(_.sum).map(((a,b,c),d)) => X(a,b,c,d))

我的问题是,在scala标准库或Scalaz中有没有更好/更清晰/更惯用的方法来实现这一点(如果d是具有幺半群实例的任意类型)?

我想我知道您想要实现什么,我找到了一种更短的方法来实现这一点,您不必使用mapValues,然后使用map,相反,您可以使用一张地图完成所有操作,如下所示:

case class X(a: String, b: String, c: String, d: Int){
  def +(that: X) = X(a,b,c, d+that.d)
}

val list = List(X("1","2","3",4),X("1","2","3",5),X("11","22","33",6),X("11","22","33",9))

list.groupBy{
  case X(a,b,c,d) => (a,b,c)}.map{ case (k,v) => X(k._1, k._2, k._3, v.reduce(_ + _).d)}

如果你能在你的类中使用sum,它会更短更干净,但是reduce也不是那么糟糕。

你能发布示例列表和示例输出吗?我不确定您在这里想要实现什么?稍后再做。您可能想看看这个scalaz示例:就我而言,没有简单的方法可以在“位置”(不需要中间集合)中执行分组和映射。scala集合上也缺少“zipWith”函数。也许将来会添加它们(java streams允许通过收集器使用映射进行分组,但使用它们的任何人都会同意它们的使用不直观)