Почему разработчики языка Java предпочитали привязывать к открытой адресации для большинства хэш-структур, за исключением некоторых, таких как ThreadLocal?

Я знаю разницу между Open Addressing и Chaining для разрешения хеш-коллизий. Большинство базовых структур данных на основе хэша, таких как HashSet, HashMap в Java, в первую очередь используют метод цепочки. Я прочитал, что ThreadLocal фактически использует схему зондирования. Поэтому я хочу понять, почему открытая адресация не так много используется в Java? Я имею в виду, что было бы сложно удалить записи, используя эту схему, в том смысле, что вы должны отметить эти ячейки некоторой специальной обработкой. Однако, похоже, что для открытой схемы адресации будет недостаточно памяти.

Изменить: я просто хочу понять возможную основную причину/причины этого дизайнерского решения. Я не хочу более тонких деталей. Также мне хотелось бы знать, почему ThreadLocal использует менее распространенную технику открытой адресации. Я думаю, что два ответа могут быть связаны друг с другом. Поэтому я предпочитаю спрашивать в том же самом вопросе.

Ответы

Ответ 1

В настоящее время я обсуждаю компактные повторные реализации HashMap и HashSet с Doug Lea. Этот конкретный вопрос не возник, но вот мои первые мысли по этому вопросу...

  • Связанные хеш-таблицы ухудшаются разумно изящно. Является ли это более высокими коэффициентами нагрузки или множеством хеш-коллизий, цепочка не ухудшается почти так же быстро, как открытая адресация.
  • Как вы уже сказали, remove - это не приятная операция в открытых таблицах. Как правило, remove является наименее распространенной операцией в хэш-таблицах, но есть приложения, для которых это более распространено, и будет отмечена плохая производительность.
  • Я также подозреваю - хотя у меня мало данных, что реализация "связанной" хэш-таблицы с открытым адресом будет значительно сложнее. LinkedHashMap записывается как подкласс HashMap и занимает большую часть деталей реализации; его несколько проще реализовать связанный список записей, когда записи являются дискретными объектами - и в этот момент вы уже больше всего привыкли к цепочке реализации.
  • Ничто в спецификации не связывает их с этой реализацией - они всегда могут свободно обходиться с ней позже.
  • Библиотеки коллекций JDK... не делают потребление памяти особенно высокоприоритетным. Память дешевая. (Вы можете или не согласны с этим, но это определенно заметная тенденция.)