繁体   English   中英

实现 scala 特性,其属性为 class object

[英]Implementing scala trait with property that is class object

我有一个简单的特征

trait SomeTrait {
  val sourceData: SourceData
}

SourceData class 具有构造函数参数p: Array[String] 现在,当我在 Object 中扩展这个特性时,我们必须为 sourceData 提供实现。

object SomeObject extends SomeTrait {
  override val sourceData: SourceData = ???
  def main(sysArgs: Array[String]){...}
}

但是,如果 class SourceData 需要来自 main 方法的 sysArgs,我如何才能在 main 方法中而不是在 SomeObject 的主体中覆盖 sourceData。 像这样:

object SomeObject extends SomeTrait {
  def main(sysArgs: Array[String]){
    override val sourceData: SourceData = new SourceData(sysArgs)
  }
}

我不想使用 var,因为 val 不变性是首选。 而且我还想拥有没有实现的特征,以强制所有子类实现 sourceData。 我还有什么其他解决方案?

在这种情况下,您无法避免可变性。 sourceData在调用main之前必须有一个值,并且main必须能够更改该值,因此该值必须是可变的。

一种选择是将sourceData def (无论如何这是个好主意)并让它访问SomeObject中的private var

trait SomeTrait {
  def sourceData: SourceData
}

object SomeObject extends SomeTrait {
  private var mySource: SourceData = ???
  def sourceData = mySource

  def main(sysArgs: Array[String]) = {
    mySource = new SourceData(sysArgs)
  }
}

这里的根本问题是有一个需要运行时初始化的顶级object 这是必需的,因为SomeObject是一个顶级object ,可以直接从代码的其他部分访问。

解决方案是依赖注入而不是全局object

trait SomeTrait {
  def sourceData: SourceData
}

object SomeObject {
  case class SomeData(sourceData: SourceData) extends SomeTrait

  def main(sysArgs: Array[String]) = {
    val theSource = SomeData(SourceData(sysArgs))

    // Pass this instance to the rest of the code that needs it
    restOfTheProgram(theSource)
  }
}

代码的SomeTrait使用传递给它的 SomeTrait 实例,而不是直接使用SomeObject

在 Scala 中没有办法做到这一点。你需要有一个 class 继承SomeTrait并从main方法实例化它。

暂无
暂无

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

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