Создать экземпляр в Kotlin и установить свойство только если не ноль - PullRequest
0 голосов
/ 18 мая 2018

У меня есть класс данных, который выглядит следующим образом:

data class MyDataCass(val x: String, val y: String, 
                      val something: Something = Something(),
                      val somethingElse : SomethingElse = SomethingElse())

Поскольку этот класс будет использоваться как в Kotlin, так и в Java, я также создал конструктор, чтобы упростить его построение изДжава.Проблема в том, что something и somethingElse являются необязательными, и я бы хотел избежать дублирования значений по умолчанию.По сути, это то, что я попробовал:

data class MyDataCass(val x: String, val y: String, 
                      val something: Something = Something(), 
                      val somethingElse : SomethingElse = SomethingElse()) {

    class Builder() {
        private lateinit var x: String
        private lateinit var y: String
        private var something: Something? = null
        private var somethingElse: SomethingElse? = null

        // builder functions to set the properties defined above
        ...

        fun build() = MyDataCass(x, y, something = ??, somethingElse = ??)
    }
}

Что я хотел бы сделать, это установить something и somethingElse , только если они были определены строителем (т.е. они не null), в противном случае я бы хотел использовать значения по умолчанию, определенные конструктором класса данных.Конечно, я мог бы изменить функцию сборки так, чтобы она выглядела так:

fun build() = if (something == null && somethingElse == null) {
        MyDataCass(x, y)
    } else if(somethingElse == null) {
        MyDataCass(x, y, something = something)
    } else {
        MyDataClass(x,y, somethingElse = somethingElse)
    }
}

, но я нахожу это довольно многословным и подверженным ошибкам.Есть ли менее многословный или более идиоматический способ достижения этого?

1 Ответ

0 голосов
/ 18 мая 2018

Это не очень хорошо поддерживается языком, если бы было хорошее решение для этого вопроса , которое также помогло бы вам.

С учетом вышесказанного я могу предложить следующее: значения по умолчанию, объявленные только один раз, но за счет дублирования другого кода:

data class MyDataCass(val x: String, val y: String,
                      val something: Something,
                      val somethingElse: SomethingElse) {

    companion object {
        operator fun invoke(x: String, y: String,
                            something: Something? = null,
                            somethingElse: SomethingElse? = null) =
                MyDataCass(x, y,
                        something ?: Something(),
                        somethingElse ?: SomethingElse())
    }

    class Builder {
        private lateinit var x: String
        private lateinit var y: String
        private var something: Something? = null
        private var somethingElse: SomethingElse? = null

        // builder functions to set the properties defined above
        // ...

        fun build() = MyDataCass(x, y, something, somethingElse)
    }
}

Таким образом, выможет продолжать использовать конструктор из Java, а в Kotlin синтаксис, который выглядит так: это вызов конструктора, а не вызов функции invoke объекта-компаньона, который имеет значения по умолчанию.Ваш класс данных, конечно, все еще имеет ненулевые типы, чтобы его было проще использовать.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...