Что лучший способ состоит в том, чтобы объединить два списка в карту (Java)?

Оператор использования просто мешает Вам квалифицировать типы, которые Вы используете. Мне лично нравится очищать их. Действительно это зависит от того, как метрика местоположения используется

56
задан Soni Vashisht 1 August 2019 в 21:42
поделиться

6 ответов

Поскольку связь "ключ-значение" неявна через индекс списка, я думаю, что решение для цикла, которое явно использует индекс списка, на самом деле довольно ясное - и короткое хорошо.

19
ответ дан 26 November 2019 в 17:09
поделиться

Используйте Clojure. всего одна строка;)

 (zipmap list1 list2)
1
ответ дан 26 November 2019 в 17:09
поделиться

Вам даже не нужно ограничиваться струнами. Немного изменив код CPerkins:

Map<K, V> <K, V> combineListsIntoOrderedMap (List<K> keys, List<V> values) {
      if (keys.size() != values.size())
          throw new IllegalArgumentException ("Cannot combine lists with dissimilar sizes");
Map<K, V> map = new LinkedHashMap<K, V>();
for (int i=0; i<keys.size(); i++) {
  map.put(keys.get(i), values.get(i));
}
return map;

}

2
ответ дан 26 November 2019 в 17:09
поделиться

ArrayUtils # toMap () не объединяет два списка в карту, но делает это для двухмерного массива (так что это не совсем то, что вы ищете, но может быть интересно для использования в будущем ...)

5
ответ дан 26 November 2019 в 17:09
поделиться

Ваше решение, приведенное выше, конечно, верно, но ваш вопрос касался ясности, я отвечу на него.

Самый простой способ объединения двух списков - чтобы поместить комбинацию в метод с красивым понятным именем. Я только что взял ваше решение и извлек его в метод здесь:

Map<String,String> combineListsIntoOrderedMap (List<String> keys, List<String> values) {
    if (keys.size() != values.size())
        throw new IllegalArgumentException ("Cannot combine lists with dissimilar sizes");
    Map<String,String> map = new LinkedHashMap<String,String>();
    for (int i=0; i<keys.size(); i++) {
        map.put(keys.get(i), values.get(i));
    }
    return map;
}

И, конечно же, ваша отрефакторная main теперь будет выглядеть так:

static public void main(String[] args) {
    List<String> names = Arrays.asList("apple,orange,pear".split(","));
    List<String> things = Arrays.asList("123,456,789".split(","));
    Map<String,String> map = combineListsIntoOrderedMap (names, things);
    System.out.println(map);
}

Я не смог устоять перед проверкой длины.

9
ответ дан 26 November 2019 в 17:09
поделиться

Я часто использую следующую идиому. Я признаю, что вопрос о том, яснее ли это

Iterator<String> i1 = names.iterator();
Iterator<String> i2 = things.iterator();
while (i1.hasNext() && i2.hasNext()) {
    map.put(i1.next(), i2.next());
}
if (i1.hasNext() || i2.hasNext()) complainAboutSizes();

, имеет то преимущество, что он также работает для Коллекций и подобных вещей без произвольного доступа или без эффективного произвольного доступа, например LinkedList, TreeSets или SQL ResultSets. Например, если вы использовали исходный алгоритм для LinkedLists, у вас есть медленный алгоритм Shlemiel the painter , который на самом деле требует n * n операций для списков длины n.

As 13ren , вы также можете использовать тот факт, что Iterator. next выдает исключение NoSuchElementException, если вы пытаетесь прочитать после конца одного списка, когда длины не совпадают. Таким образом, вы получите более краткий, но, возможно, немного сбивающий с толку вариант:

Iterator<String> i1 = names.iterator();
Iterator<String> i2 = things.iterator();
while (i1.hasNext() || i2.hasNext()) map.put(i1.next(), i2.next());
41
ответ дан 26 November 2019 в 17:09
поделиться
Другие вопросы по тегам:

Похожие вопросы: