如何在 Kotlin 中克隆对象(不是数据 class)
How to clone object in Kotlin (not data class)
我需要为某些基 class 定义一些二元运算(如矩阵加法),但如果应用于派生 class,则需要它 return 派生 class .为此,我需要在编译时不知道它是 class 的情况下克隆派生的 class,例如
class Matrix private constructor(private val data: DataClass) {
public constructor(...) : this(...) {
...
}
operator fun times(ano: Matrix) : Matrix {
return Matrix(data.specialOp(ano.data))
}
}
class EnhancedMatrix {
...
}
fun main() {
val a = EnhancedMaptrix(...)
val b = EnhancedMaptrix(...)
val c = a * b;
println(c is EnhancedMartrix) // should be true w/o explicit overriding of `times`
}
可能吗?
不使用反射的最简单方法可能是通过子类提供一个工厂:
open class Matrix(
private val data: DataClass,
private val factory: (DataClass) -> Matrix
) {
operator fun times(ano: Matrix) : Matrix {
return factory(data.specialOp(ano.data))
}
}
class EnhancedMatrix(data: DataClass) : Matrix(data, ::EnhancedMatrix)
此外,如果我们希望 c
不仅在运行时被初始化为 EnhancedMatrix
对象,而且在编译时被解析为 EnhancedMatrix
类型,那么这个更复杂,但仍然可能。我们必须像这样使用 self-referencing 通用类型:
open class Matrix<T : Matrix<T>>(
val data: DataClass,
private val factory: (DataClass) -> T
) {
operator fun times(ano: Matrix<*>) : T {
return factory(data.specialOp(ano.data))
}
}
class EnhancedMatrix(data: DataClass) : Matrix<EnhancedMatrix>(data, ::EnhancedMatrix)
Matrix
由其特定类型参数化,因此如果我们在 EnhancedMatrix
(即 Matrix<EnhancedMatrix>
)上使用 times()
,那么它本身 returns EnhancedMatrix
还有。请注意这个解决方案非常复杂,不容易理解,所以只有在真正需要时才使用它。
可能不是您想要的,但您能否为 EnhancedMatrix 提供一个以 Matrix 作为参数的辅助构造函数?
open class Matrix {
operator fun times(ano: Matrix) : Matrix {
return Matrix()
}
}
class EnhancedMatrix() : Matrix() {
constructor(m: Matrix) : this() { }
}
fun main() {
val a = EnhancedMatrix()
val b = EnhancedMatrix()
val c = EnhancedMatrix(a * b)
println(c is EnhancedMatrix) // should be true w/o explicit overriding of `times`
println(c is Matrix)
}
我需要为某些基 class 定义一些二元运算(如矩阵加法),但如果应用于派生 class,则需要它 return 派生 class .为此,我需要在编译时不知道它是 class 的情况下克隆派生的 class,例如
class Matrix private constructor(private val data: DataClass) {
public constructor(...) : this(...) {
...
}
operator fun times(ano: Matrix) : Matrix {
return Matrix(data.specialOp(ano.data))
}
}
class EnhancedMatrix {
...
}
fun main() {
val a = EnhancedMaptrix(...)
val b = EnhancedMaptrix(...)
val c = a * b;
println(c is EnhancedMartrix) // should be true w/o explicit overriding of `times`
}
可能吗?
不使用反射的最简单方法可能是通过子类提供一个工厂:
open class Matrix(
private val data: DataClass,
private val factory: (DataClass) -> Matrix
) {
operator fun times(ano: Matrix) : Matrix {
return factory(data.specialOp(ano.data))
}
}
class EnhancedMatrix(data: DataClass) : Matrix(data, ::EnhancedMatrix)
此外,如果我们希望 c
不仅在运行时被初始化为 EnhancedMatrix
对象,而且在编译时被解析为 EnhancedMatrix
类型,那么这个更复杂,但仍然可能。我们必须像这样使用 self-referencing 通用类型:
open class Matrix<T : Matrix<T>>(
val data: DataClass,
private val factory: (DataClass) -> T
) {
operator fun times(ano: Matrix<*>) : T {
return factory(data.specialOp(ano.data))
}
}
class EnhancedMatrix(data: DataClass) : Matrix<EnhancedMatrix>(data, ::EnhancedMatrix)
Matrix
由其特定类型参数化,因此如果我们在 EnhancedMatrix
(即 Matrix<EnhancedMatrix>
)上使用 times()
,那么它本身 returns EnhancedMatrix
还有。请注意这个解决方案非常复杂,不容易理解,所以只有在真正需要时才使用它。
可能不是您想要的,但您能否为 EnhancedMatrix 提供一个以 Matrix 作为参数的辅助构造函数?
open class Matrix {
operator fun times(ano: Matrix) : Matrix {
return Matrix()
}
}
class EnhancedMatrix() : Matrix() {
constructor(m: Matrix) : this() { }
}
fun main() {
val a = EnhancedMatrix()
val b = EnhancedMatrix()
val c = EnhancedMatrix(a * b)
println(c is EnhancedMatrix) // should be true w/o explicit overriding of `times`
println(c is Matrix)
}