我想用定义的apply方法创建工厂对象,这将创建基础案例类 - 这是一个示例代码
object DeptEntry {
def apply(url: String, fullName: String, address: String, city: String): DeptEntry = {
new DeptEntry(url.toLowerCase, fullName.toLowerCase, address.toLowerCase, city.toLowerCase)
}
}
case class DeptEntry private(url: String, fullName: String, address: String, city: String) {
}
问题是对象和case类的构造函数中的apply方法具有相同的参数列表。 所以编译器给了我这个错误:
method apply is defined twice
conflicting symbols both originated in file 'DeptEntry.scala'
case class DeptEntry private(url: String, fullName: String,
^
这个问题是否有解决方法?
非常感谢
答案 0 :(得分:3)
声明案例类abstract
object DeptEntry {
def apply(url: String, fullName: String, address: String, city: String): DeptEntry = {
new DeptEntry(url.toLowerCase, fullName.toLowerCase, address.toLowerCase, city.toLowerCase) {}
}
}
abstract case class DeptEntry private(url: String, fullName: String, address: String, city: String) {
}
根据Iulian Dragos commenting on SI-844
的说法答案 1 :(得分:0)
您可以将DeptEntry设为“普通”(非案例类)类。或者,您可以在Object中使用具有不同名称的Method。 (例如DeptEntry.lowerCase(...))
答案 2 :(得分:0)
当您创建case class
时,Scala编译器会自动为您生成一个带有apply方法的伴随对象。此apply方法与case类的构造函数具有相同的参数。这就是您遇到此编译器错误的原因。你不能覆盖它的事实确保了这样的东西:
val inputUrl = "MyUrl://blabla"
val DeptEntry(outputUrl, _, _, _) = DeptEntry(inputUrl, "", "", "")
outputUrl == inputUrl
尝试从类定义中删除case
并自行编写随播广告对象的apply
(如果需要提取,则为unapply
)(toString
,{{1}如果需要,可以在类本身中使用equals
。
答案 3 :(得分:0)
一种可能性是从您的用户隐藏(一点点)该类:
sealed trait DeptEntry
object DeptEntry {
def apply(url: String, fullName: String,
address: String, city: String): DeptEntry = // ...
case class Value protected[DeptEntry](
url: String, fullName: String, address: String, city: String
)
}
这种方式没有冲突,如果需要,您仍然可以在DeptEntry.Value
上进行模式匹配。如果此解决方案方便与否,这取决于您的用例。如果您希望特征具有正确的val
s,则可以将其声明为
sealed trait DeptEntry {
val url: String
val fullName: String
val address: String
val city: String
}
,case class
中的字段将覆盖它们。