我在Kotlin上还很陌生,我一直坚持制作类似于此Swift结构的数据类:
struct AppVersion {
let major: Int
let minor: Int
let patch: Int
}
extension AppVersion {
init(version: String) {
let parts = version.split(separator: ".")
let numbers = parts.map { Int($0) ?? 0 }
self.init(major: numbers[0], minor: numbers[1], patch: numbers[2])
}
}
为清楚起见,我们仅假设toInt()
不抛出,并且版本字符串中始终有3个组件。
我有两种可行的解决方案。使用伴随对象:
data class AppVersion (val major: Int, val minor: Int, val patch: Int) {
companion object {
fun fromString(version: String): AppVersion {
val parts = version.split(".").map { it.toInt() }
return AppVersion(parts[0], parts[1], parts[2])
}
}
}
或者写一些看起来很糟糕的东西:
data class AppVersion (val major: Int, val minor: Int, val patch: Int) {
constructor(version: String) : this(
version.split(".")[0].toInt(),
version.split(".")[1].toInt(),
version.split(".")[2].toInt()
)
}
但是为便利构造函数使用更长的方法名称似乎很奇怪,第二个选择也很糟糕。
是否可能这样?
data class AppVersion (val major: Int, val minor: Int, val patch: Int) {
constructor(version: String): this(0, 0, 0) {
val parts = version.split(".").map { it.toInt() }
this(parts[0], parts[1], parts[2])
}
}
答案 0 :(得分:1)
超级构造函数调用必须是构造函数的第一条语句,并且只能出现一次。另外,每个val
必须初始化一次;您无法将其初始化为0,然后改变主意。这是JVM的限制。
与您的第一个解决方案一样,Kotlin中的惯用解决方案是使用工厂方法。