O(1)从mutable.Map转换为immutable.Map?

Itt*_*ayD 14 scala scala-collections

有没有办法在O(1)时间内将可变映射转换(换行)为不可变(也就是说,不是通过复制值,而是类似于在JavaConversions中完成的操作)

ret*_*nym 6

正如托马斯指出的那样,只读视图是O(1).但是只读不等同于不变性.

" Fighting Bit Rot "论文中描述了这种差异:

所有集合类都保存在包scala.collection中.这个包有三个子包:mutable,immutable和generic.大多数集合以三种形式存在,具体取决于它们的可变性.

scala.collection.immutable包中的集合保证对每个人都是不可变的.这意味着可以依赖于随着时间的推移访问相同的集合值将始终产生具有相同元素的集合的事实.已知包scala.collection.mutable中的集合具有一些可以更改集合的操作.

包scala.collection中的集合可以是可变的也可以是不可变的.例如,collection.Seq [T]是collection.immutable.Seq [T]和collection.mutable.Seq [T]的超类.通常,包scala中的根集合.collection定义与不可变集合相同的接口,并且包scala.collection.mutable中的可变集合通常会向此不可变接口添加一些破坏性修改操作.根集合和不可变集合之间的区别在于,不可变集合的用户可以保证任何人都不能改变集合,而根集合的用户必须承担其他人的修改,即使他们自己也不能进行任何修改.

也许这只是一个简单的升级.

scala> val mm = collection.mutable.Map(1 -> 2)
mm: scala.collection.mutable.Map[Int,Int] = Map(1 -> 2)

scala> val readOnly = mm : collection.Map[Int, Int]
readOnly: scala.collection.Map[Int,Int] = Map(1 -> 2)
Run Code Online (Sandbox Code Playgroud)

  • cast和map.readOnly之间的区别在于用户可以将collection.Map转换回可变映射或使用反射来更改映射. (2认同)

Tho*_*ung 5

可变映射有只读投影

scala> collection.mutable.Map(1->2).readOnly
res0: scala.collection.Map[Int,Int] = ro-Map(1 -> 2)
Run Code Online (Sandbox Code Playgroud)

正如oxbow_lakes 指出的,底层 Map 仍然是可变的,并且在只读投影发布给客户端后可能会发生变化。必须在管理地图的代码中解决不变性的错觉。

  • 看起来这是一个 2.7 方法。它在 2.8.0-Beta1 中被注释掉了,夜间文档没有显示它。 (6认同)
  • 这似乎已弃用,请使用`collection.mutable.Map(1->2).toMap` (2认同)
  • 不幸的是,`toMap` 复制了地图条目。我认为我们正在寻找一种用不可变接口包装地图的东西。 (2认同)