Как заставить .NET Hashtable работать так же, как Java Hashtable - PullRequest
1 голос
/ 07 января 2011

Когда я добавляю некоторые элементы в Java Hashtable, их порядок отличается от .NET Hashtable. Можно ли как-то убедиться, что .NET Hashtable будет иметь тот же порядок, что и Java Hashtable?


Я пытаюсь портировать Java-код на C #. Код Java использует Hashtable для отслеживания некоторых данных. Когда я проверяю, чтобы увидеть порядок , данные извлекаются, когда я перебираю либо Java Hashtable, либо .NET Hashtable (через Enumerator), каждый из них последовательно имеет одинаковые данные, в том же порядке ... но каждый код на основе имеет другой порядок.

Можно ли как-нибудь сделать так, чтобы данные .NET Hashtable были в том же порядке, что и Java Hashtable?

Я понимаю, что Hashtable не обрабатывает заказы - поэтому я чувствую, что ничего нельзя сделать. Я также не могу изменить тип данных в коде Java с .. скажем .. Hashtable на что-то другое.

Вот некоторые данные, иллюстрирующие мою ситуацию.

Данные, добавленные последовательно для любой кодовой базы: -

  1. число | someData
  2. pagenum | someData
  3. х | someData
  4. верх | someData

Java-код:

private Hashtable identifiers = new Hashtable();
...
identifiers.put(symbol, identifier);

Вывод Java через итератор через перечислитель:

alt text

.NET код:

private Hashtable Identifiers = new Hashtable();
...
Identifiers.Add(symbol, identifier);

.NET вывод через итерацию по перечислителю.

alt text

Есть идеи или предложения?

Ответы [ 7 ]

8 голосов
/ 07 января 2011

К сожалению, если не считать изменения типа коллекции, на самом деле нет никакого способа обойти это. Hashtables не гарантирует порядок (как вы упомянули в своем посте).

Все сводится к следующему:

Если порядок важен, Hashtable - неправильная структура данных.

3 голосов
/ 07 января 2011

Вы не можете изменить этот порядок, если не извлекать ключи и не сортировать их каким-либо образом (или не использовать упорядоченный словарь). Порядок итераций в любой из реализаций хеш-таблиц, которые вы используете, не указан, и поэтому использование определенного порядка означает, что ваш код не работает. Порядок итераций в Java даже не гарантированно останется таким же в будущем версии JDK.

2 голосов
/ 07 января 2011

Порядок в общей хэш-таблице непредсказуем.Это то, что вы испытываете.Если вы пытаетесь запустить сравнительные тесты и вам нужен определенный порядок, вы должны использовать упорядоченные карты на концах ОБА Иначе вряд ли можно предсказать результат.

1 голос
/ 07 января 2011

Это ужасное решение, но по вашему описанию у вас нет другого выхода.

Вы можете взять исходники класса Java Hastable и перенести их на C #.Удалите все ненужное, например, итераторы и keySet, equals, и у вас будет довольно маленький класс (несколько десятков строк, которые я ожидаю).Преобразование его в C # должно быть тривиальным.

Естественно, вы не должны использовать этот новый класс ни для чего, кроме совместимости с Java.И отправка сообщения об ошибке исходному поставщику приложения тоже может быть приятной:)

1 голос
/ 07 января 2011

Вы можете использовать LinkedHashMap в Java, и Recursion Software делает его доступным для C # согласно этой записи .

Я не пробовал это решение.

1 голос
/ 07 января 2011

Я согласен с другими ответами, но все же Hashtable устарела.Вы должны всегда использовать общий класс Dictionary.Существует также SortedDictionary, имя класса говорит все.Вы можете перевернуть или отсортировать его содержимое, посмотрите здесь Обратный отсортированный словарь в .NET

0 голосов
/ 07 января 2011

Вы можете попытаться реализовать (в .NET) свои собственные IHashCodeProvider и IComparer и передать их конструктору Hashtable.Из опубликованного вами примера видно, что записи отсортированы по возрастанию (.NET) и по убыванию (Java) по ключу, поэтому вам потребуется компаратор, который инвертирует порядок.

...