繁体   English   中英

如何在Scala中默认为不可变Seq?

[英]How to default to immutable Seq in scala?

我今天了解到,scala的Seq可能意味着可变或不变的Seq都可以满足其类型别名。 (我偶然发现了一个谈论它的博客 。)

在我的代码库中,我尝试遵循函数式编程最佳实践,尽管我确实假定Seq强制执行不可变序列,但可能并非如此,因此会导致意外副作用的切入点。

为了防止可变的Seq,我可以使用带有以下内容的Sequence键入我的函数:

我希望在每个文件中使用Seq scala.collection.immutable.Seq

我也不喜欢在我的代码库中读取immutable.Seq

对我来说, Seq行为应类似于Set别名,并且默认情况下是不可变的。

有没有一种方法可以使我的项目使用默认的Seq别名指向其不变的副本,而又不妨碍供应商的进口?

我不建议您尝试破坏默认的Scala行为。 除非您定义自己的函数以接收任何输入并返回该输入的不可变Seq,否则我认为仅使用immutable.Seq是最安全的

您可以随时尝试以下操作(未经全面测试):

def seq(inputs: Any*): scala.collection.immutable.Seq[Any] = {
  scala.collection.immutable.Seq(inputs)
}

scala> seq("hi", true)
res0: scala.collection.immutable.Seq[Any] = List(WrappedArray(hi, true))

scala> seq(1, 'c', "string", false)
res1: scala.collection.immutable.Seq[Any] = List(WrappedArray(1, c, string, false))

编辑:

正如jwvh所指出的,该选项不是理想的。 如果您坚持要创建自己的函数,那么建议使用像James Whiteley这样的泛型类型会更好:

def seq[T](inputs: T*): scala.collection.immutable.Seq[T] =
  scala.collection.immutable.Seq(inputs).flatten

输出:

scala> seq("hi", true)
res0: scala.collection.immutable.Seq[Any] = List(hi, true)

但我要重申-可能最好是在需要的地方使用immutable.Seq ,或者找到另一个要使用的集合类型。

好吧,在阅读了(已有4年历史的)博客文章之后,我真的认为这不是什么大问题。

默认的Seq()collection.Seq本身不是可变的,但它是可变和不可变变量的父代。 因此,创建并传递默认Seq集合的代码不会受到影响,但是接受Seq参数的代码可能会收到mutable.Seq 但这仅是不可变性的前提条件,例如线程安全性,这只是一个问题。

底线:在这些文件的顶部放置一个import collection.immutable.Seq ,其中:

  1. 您无法控制的客户端代码可能会向您发送可变的Seq ,并且
  2. 收到的收藏品的不变性至关重要。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM