1

我有以下情况:我收到一个特定类型的迭代器,想把它变成一个特定的地图。我觉得可能有一种非常简单的方法可以做到这一点,但我似乎无法弄清楚:) 这是一些让事情更容易理解的代码:(我将案例类缩短到最低限度)

case class Fu(title: String)
case class Bar(name: String)
case class Match(f: Fu, b: Bar)
case class Result(name: String, fus: List[Fu])

val input: Iterator[Match] = ...

我最终想要的是这样的:

val output: Iterator[Result]

这是棘手的部分:匹配是独一无二的,但自然而然,每个 Fu 可以匹配多个 Bar。我基本上希望将所有具有相同 Bar 的火柴拆开,并将它们的 Fus 放入一个列表中。有点像 Map[Bar, List[Fu]],只是我有一个类型。Result 类也可以使用 Bars 而不是名称 String,但我真的不需要其他 Bar 信息。但这无关紧要。输出类型也不是那么重要,无论是 Iterator、Iterable、List 还是其他任何类型。只要映射工作正常。

起初,我认为 Iterable 上的 groupBy 会完全符合我的要求,但我要么不知道如何正确使用 groupBy,要么它是该工作的错误功能 :) 使用 map 似乎是一个好的开始,但接下来该怎么做我建立清单?我可以轻松地将每个 Match 变成一个 Result,但最终我会得到许多具有相同名称的 Result 对象......

非常感谢,任何帮助表示赞赏!

编辑:也许我应该明确指出这与匹配字符串无关。它们只是两个案例类的示例属性。所有 Fus 和 Bars 都已正确匹配到 Match 对象中。

4

1 回答 1

5

你在正确的轨道上groupBy。下面是它的外观:

val input: Iterator[Match] = Iterator(
  Match(Fu("A"), Bar("1")),
  Match(Fu("B"), Bar("2")),
  Match(Fu("C"), Bar("1")),
  Match(Fu("D"), Bar("2")))

val output =
  input.toList
    .groupBy { case Match(f, Bar(name)) => name }
    .map { case (name, fus) => Result(name, fus.map(_.f)) }

 output foreach println                         //> Result(1,List(Fu(A), Fu(C)))
                                                //| Result(2,List(Fu(B), Fu(D)))
于 2012-12-18T04:40:08.030 回答