2015-12-13 2 views
13

Я понимание проблемы, почему Java HashMap несовместима с Java Map в Котлин:Содержит ли java.util.HashMap java.util.Map в Котлине?

val map : java.util.Map<Int, Int> = java.util.HashMap<Int, Int>() 
            // ERROR: Type mismatch 

Является ли это ошибка или он намеренно применяются, чтобы быть ошибка в Котлин?


Вот второй пример с Java на Котлин компилятором. Посмотрите на этом примере файл Java:

public class Test { 
    public static void main(String[] args) { 
     java.util.Map<Integer, Integer> map = new java.util.HashMap<>(); 
     insertValue(map); 
    } 

    private static void insertValue(java.util.Map<Integer, Integer> map) { 
     map.putIfAbsent(0, 1); 
    } 
} 

Запуск «Преобразование Java в Котлин» результатов в этом файле:

object Test { 
    @JvmStatic fun main(args: Array<String>) { 
     val map = java.util.HashMap<Int, Int>() 
     insertValue(map) 
    } 

    private fun insertValue(map: Map<Int, Int>) { 
     map.putIfAbsent(0, 1) // ERROR! Unresolved reference 
    } 
} 

Если я пытаюсь изменить его, чтобы отразить больше исходного файла, где insertValue ожидали Java java.util.Map, я получаю другую ошибку:

object Test { 
    @JvmStatic fun main(args: Array<String>) { 
     val map = java.util.HashMap<Int, Int>() 
     insertValue(map) // ERROR: Type mismatch 
    } 

    private fun insertValue(map: java.util.Map<Int, Int>) { 
     map.putIfAbsent(0, 1) // is now OK 
    } 
} 

ответ

13

В Котлин, java.util.HashMap, во время компиляции, не реализует java.util.Map, но реализует kotlin.collections.MutableMap, который проходит только для чтения kotlin.collections.Map.

Это из-за Kotlin's mapped types. См. Коллекции в Kotlin M3 is Out! для получения более подробной информации.

MutableMap не определяет putIfAbsent, но имеет функцию расширения getOrPut.

+1

Вы уверены? Я думал, что «котлин.MutableMap' не существует во время выполнения? – voddan

+0

Исправить. Вот почему я написал «во время компиляции» в своем ответе. Kotlin [сопоставленные типы] (https://kotlinlang.org/docs/reference/java-interop.html#mapped-types) доступны во время компиляции, а затем отображаются во время выполнения для разных типов. Подробнее о типах плат [здесь] (https://kotlinlang.org/docs/reference/java-interop.html#null-safety-and-platform-types) и [здесь] (https://kotlinlang.org/ документы/ссылки/Java-interop.html # нотация-для-платформ-типов). – mfulton26

0

Я думаю, это ошибка. Вы можете сообщить об этом там https://youtrack.jetbrains.com/issues/KT

Но до сих пор, putIfAbsent особенность Java 8, но не поддерживается в Котлин (MutableMap интерфейс отсутствует этот метод).

+0

Почему пустые голоса? –

+1

Я подозреваю, что пустые голоса были из-за отсутствия ссылок, подтверждающих этот ответ. например Этот ответ, возможно, считался более полезным для некоторых, если была предоставлена ​​ссылка на проблему или соответствующую документацию о [вызове Java из Kotlin] (https://kotlinlang.org/docs/reference/java-interop.html), в котором указаны/показывает, что сборники Java не рассматриваются специально в Котлине. – mfulton26

+0

Лично я ценю ответ, но я бы хотел, чтобы он ссылался на конкретную проблему или какую-то документацию, подтверждающую, что это может быть ошибка. – mfulton26

3

Я создал отчет об ошибке, в первую очередь для «Java в Котлин» конвертер, который генерирует неверный код Котлин в моем исходном примере:

KT-10400 Java to Kotlin converter: converting Java Code where a java.util.HashMap is accessed through the java.util.Map interface fails

Я также отметил, что java.util.HashMap не реализует java.util.Map, но я оставляю это разработчикам Kotlin, чтобы решить, является ли это ошибкой, или компилятор прав отклонить его.

ОБНОВЛЕНИЕ: Исправлена ​​ошибка (commit 5e231db6).

Смежные вопросы