如何在 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)
}