Устали с пытается решить проблему с этим кодом:Ошибка в HashMap/ArrayList или неправильный код?
public class MapTest {
static class T{
static class K{}
}
static Map<List<T.K>, List<String>> map = new HashMap<>();
static List<String> test(List<T.K> list, String s){
List<String> l = map.get(list);
if (l == null){
l = new ArrayList<String>();
System.out.println("New value()");
map.put(list, l);
}
l.add(s);
return l;
}
public static void main(String s[]){
ArrayList<T.K> list = new ArrayList<T.K>();
test(list, "TEST");
list.add(new T.K());
List<String> l = test(list, "TEST1");
System.out.println(l.size());
}
}
Он должен создать новый список-значение для отображения только один раз, но выход следующим образом:
New value
New value
1
это что-то случилось с хэш-кодом списка после того, как я вставляю в него значение. Я ожидаю, что «новое значение» появится только один раз, а размер будет равен 2, а не 1. это просто проблема с JVM или что-то более общее? mine one is Oracle JVM 1.8.0_65
В этом примере показано, почему плохая идея использовать изменяемые типы ключей карты. 'list.add (new T.K());' заставляет список генерировать другой хэш-код, поскольку он больше не пуст, поэтому карта больше не может найти существующий экземпляр. Btw: JavaDoc из ['List # hashCode'] (https://docs.oracle.com/javase/7/docs/api/java/util/List.html#hashCode%28%29) очень хорошо объясняет его поведение , – Tom
В целом: стандартные библиотеки java не имеют ошибок. Если у них есть ошибки, они чрезвычайно тонкие. Смысл: можно с большой уверенностью предположить, что библиотека права; и что эти идеи/предположения ... нет. – GhostCat
Когда вы добавили новый T.K в свой список, изменилось значение toString(), поэтому он добавляет другое значение в ваш HashMap. Теперь ключ отличается. Выведите свой список на консоль внутри вашего метода test(), чтобы понять, что я имею в виду. – ManoDestra