Kotlin: универсальный c параметр функции приведения - PullRequest
0 голосов
/ 29 марта 2020

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

Вот пример для Long:

    private fun <T> castLong(value: Long, clazz: Class<out T>): T {
        // map lookup removed for simplicity
        return when (clazz) {
            String::class.java -> { value.toString() }
            else -> { throw IllegalArgumentException("Unsupported Cast") }
        }
    }

Где T является классом желаемого возвращаемого значения - скажем, String. Нужно уметь звонить castLong(aLongValue, String::class.java) и получать экземпляр String. Но компилятор говорит:

Несоответствие типов: предполагаемый тип - String, но ожидалось T

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

1 Ответ

2 голосов
/ 29 марта 2020

Это происходит потому, что он не может умно разыграть String в T, вы должны разыграть его вручную.

Более того, поскольку вы сказали, что делаете свои первые шаги в Kotlin, я оставьте здесь два других «совета», не связанных строго с вашим вопросом:

  1. вы можете получить класс T, сделав его reified
  2. скобками кейса, используя when не требуется, если регистр состоит из одной строки
private inline fun <reified T> castLong(value: Long): T {
    // map lookup removed for simplicity
    return when (T::class.java) {
        String::class.java -> value.toString()
        else -> throw IllegalArgumentException("Unsupported Cast")
    } as T
}

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