Scala 接受可变集合,并承诺不更改它

Scala 接受可变集合,并承诺不更改它,scala,collections,parameter-passing,Scala,Collections,Parameter Passing,通常,如果我想在我的方法中“保证”我不会更改传递的参数,我会接受它作为一个不可变的集合。但是,我希望允许调用方传递可变集合,但在我的方法中仍然保证无论如何都不会更改它 我特别谈论的是IndexedSeq大多数(如果不是全部的话)集合,它们有一个可变和不可变的版本,有一个公共的超类 对于IndexedSeq而言,它是traitscala.collection.IndexedSeq def foo(seq:scala.collection.IndexedSeq)=…… 将同时接受scala.coll

通常,如果我想在我的方法中“保证”我不会更改传递的参数,我会接受它作为一个不可变的集合。但是,我希望允许调用方传递可变集合,但在我的方法中仍然保证无论如何都不会更改它

我特别谈论的是IndexedSeq

大多数(如果不是全部的话)集合,它们有一个可变和不可变的版本,有一个公共的超类

对于
IndexedSeq
而言,它是trait
scala.collection.IndexedSeq

def foo(seq:scala.collection.IndexedSeq)=……

将同时接受
scala.collection.immutable.IndexedSeq
scala.collection.mutable.IndexedSeq

scala.collection.IndexedSeq也没有修改集合的方法

但是这不是保证,因为您仍然可以执行以下操作:

def foo(seq: scala.collection.IndexedSeq) = seq match {
  case s: scala.collection.mutable.IndexedSeq => ... //use modifying methods on s
  case _ => ... //whatever
}
最后,您仍然可以访问可能改变状态的方法。优点是您必须(主动)匹配它,以便访问这些方法。因此,只有当你意识到这一点时,你才能这样做


承诺?取决于您。

为什么不使用trait
scala.collection.IndexedSeq
?通过这种方式,不可变和可变版本都可以被传递,并且您不能意外地更改数据,因为trait没有用于它的方法。@Kigyo您应该将其转化为一个答案。这真的是“正常”完成的吗?那太啰嗦了,我不知道你的意思。你能详细说明一下吗?键入collection.IndexedSeq[Int]、mutable.IndexedSeq[Int]、immutable.IndexedSeq[Int]、immutable.IndexedSeq[Int],etc@Spacemonkey是的,就是这样做的。Scala的妙处在于,您只需编写一次类型,编译器就能在代码的其余部分推断出类型。@Spacemonkey我的意思是,您可以这样做
val x=Seq();val y=x
。但是,例如在Java中,您需要
List x=new LinkedList();列表y=x