dvkch
dvkch

Reputation: 1109

Kotlin data class convenience constructor

I'm pretty new on Kotlin and I've been stuck on making a data class similar to this Swift struct:

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])
    }
}

For the sake of clarity we'll just assume toInt() doesn't throw and there are always 3 components in the version string.

I have two solutions that work. Using a companion object:

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])
        }
    }
}

Or writing something that looks really bad:

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()
    )
}

But having a longer method name for a convenience constructor seems weird and the second option is just bad.

Is something like this possible ?

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])
    }
}

Upvotes: 1

Views: 1340

Answers (1)

yole
yole

Reputation: 97138

A super constructor call must be the first statement of a constructor, and can be present only once. Also, each val must be initialized exactly once; you can't initialize it with 0 and then change your mind. This is a JVM restriction.

The idiomatic solution in Kotlin is to use a factory method, as in your first solution.

Upvotes: 1

Related Questions