将 Scala 映射转换为列表

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/6998676/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-10-22 03:20:22  来源:igfitidea点击:

Converting a Scala Map to a List

scaladata-structures

提问by bmatheny

I have a map that I need to map to a different type, and the result needs to be a List. I have two ways (seemingly) to accomplish what I want, since calling map on a map seems to always result in a map. Assuming I have some map that looks like:

我有一张需要映射到不同类型的地图,结果需要是一个列表。我有两种方法(看似)来完成我想要的,因为在地图上调用 map 似乎总是会产生一张地图。假设我有一些看起来像的地图:

val input = Map[String, List[Int]]("rk1" -> List(1,2,3), "rk2" -> List(4,5,6))

I can either do:

我可以这样做:

val output = input.map{ case(k,v) => (k.getBytes, v) } toList

Or:

或者:

val output = input.foldRight(List[Pair[Array[Byte], List[Int]]]()){ (el, res) =>
  (el._1.getBytes, el._2) :: res
}

In the first example I convert the type, and then call toList. I assume the runtime is something like O(n*2)and the space required is n*2. In the second example, I convert the type and generate the list in one go. I assume the runtime is O(n)and the space required is n.

在第一个示例中,我转换了类型,然后调用 toList。我假设运行时是这样的O(n*2),所需的空间是n*2. 在第二个示例中,我一次转换类型并生成列表。我假设运行时为O(n),所需空间为n.

My question is, are these essentially identical or does the second conversion cut down on memory/time/etc? Additionally, where can I find information on storage and runtime costs of various scala conversions?

我的问题是,这些本质上是相同的还是第二次转换会减少内存/时间/等?此外,我在哪里可以找到有关各种 Scala 转换的存储和运行时成本的信息?

Thanks in advance.

提前致谢。

采纳答案by Jean-Philippe Pellet

My favorite way to do this kind of things is like this:

我最喜欢做这种事情的方式是这样的:

input.map { case (k,v) => (k.getBytes, v) }(collection.breakOut): List[(Array[Byte], List[Int])]

With this syntax, you are passing to mapthe builder it needs to reconstruct the resulting collection. (Actually, not a builder, but a builder factory. Read more about Scala's CanBuildFroms if you are interested.) collection.breakOutcan exactly be used when you want to change from one collection type to another while doing a map, flatMap, etc. — the only bad part is that you have to use the full type annotation for it to be effective (here, I used a type ascription after the expression). Then, there's no intermediary collection being built, and the list is constructed whilemapping.

使用此语法,您将传递给map构建器以重建结果集合。(其实,不是一个建设者,但建设者工厂了解更多关于Scala的。CanBuildFrom■如果你有兴趣。)collection.breakOut当你想改变一个集合类型到另一边做一个能准确使用mapflatMap等等-唯一不好的部分是您必须使用完整的类型注释才能使其有效(在这里,我在表达式之后使用了类型归属)。然后,没有构建中间集合,并且映射时构建列表。

回答by Ben James

Mapping over a view in the first example could cut down on the space requirement for a large map:

在第一个示例中映射视图可以减少大地图的空间需求:

val output = input.view.map{ case(k,v) => (k.getBytes, v) } toList