gpt4 book ai didi

scala - 我可以自定义案例类中的值组件吗?

转载 作者:行者123 更新时间:2023-12-04 19:47:47 25 4
gpt4 key购买 nike

假设我在库中有一些案例类:

case class MyClass(a: Int, b: Int)

后来发现我的库中有一个错误,我需要对这些参数之一应用一些额外的逻辑以保持工作正常,以便从用户的角度来看可能会发生这种情况:

val x = MyClass(1, 2)
println(x.a) // prints '3' or whatever I happen to compute for 'a'

换句话说,x.a 的最终值不一定是传递给构造函数的值。我知道这看起来很疯狂,但相信我,我需要它。在大多数情况下,x.a 仍会返回传递给构造函数的任何内容,但构造函数参数有一个值会导致错误,我需要对其进行转换。

我看到有两种方法可以实现这一点。我可以让 a 成为 var:

case class MyClass(var a: Int, b: Int) {
a = someComputation()
}

但随后该类变得可变,因为可以从外部设置 a。如果我可以删除或“隐藏”生成的 setter,我的问题就会得到解决,但这似乎是不可能的。如果我添加

private def a_=(newA: Int) {}

它不会覆盖 var 生成的 setter,因此它会看到两个方法定义并且不会编译。

第二个选项是创建一个与构造函数参数分开的字段/方法:

case class MyClass(private val _a: Int, b: Int) {
val a = someComputation(a)
}

_a 用于所有特殊生成方法,如 equalstoString 等,而自定义字段 a 没有特色。

有没有什么方法可以在不影响 API 其余部分的情况下转换构造函数参数?

最佳答案

我要做的是重写伴随对象上的 apply 方法,以使用正确的计算创建 MyClass 的实例。

object MyClass {
def apply(a: Int, b: Int) = new MyClass(someComputation(a),b))
}

那么你可以像val x = MyClass(1, 2)那样调用它,但是你不能像val x = new MyClass(1, 2)那样调用它 如果您仍然希望进行计算。

显然以上所有在 REPL 之外都不起作用。

相反,我会在伴随对象上选择另一种方法,这不是一个很好的解决方案,但它应该有效:

object MyClass {
def create(a: Int, b: Int) = new MyClass(someComputation(a),b))
}

关于scala - 我可以自定义案例类中的值组件吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36431915/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com