Некоторые мысли, а не полноценное решение.
Если нет определенных доказательств того, что сам поиск является узким местом (не используйте свое «чувство» для обнаружения узких мест, используйте профилировщик кода), я бы придерживался IntList ... Если время, потраченное на фактический поиск / insert / delete не составляет по крайней мере 20% от общего времени процессора, даже не беспокойтесь.
Если вам все еще нужна хеш-таблица, тогда ...
Не преобразовывать в строку. Преобразование выделит новую строку из кучи, что намного дороже, чем сам поиск. Используйте int64 по модулю некоторого хитро выбранного простого числа в качестве ключа хеширования.
Hashtables даст вам O (1), только если они достаточно велики. В противном случае вы получите большое количество записей с одинаковым хэш-ключом. Сделайте это слишком коротким, вы будете тратить свое время на поиск (линейно!) В связанном списке. Сделайте его слишком большим, и вы потеряете память.
Имейте в виду, что хеш-таблицы требуют некоторой формы связанного списка, чтобы все записи имели один и тот же ключ. Этот связанный список должен быть реализован либо путем добавления указателя «next» в объектах полезной нагрузки (который нарушает инкапсуляцию - объект не должен знать, что он хранится в хэш-таблице), либо путем выделения небольшого вспомогательного объекта. Это распределение, вероятно, будет намного более дорогостоящим, чем O (log) отсортированного списка.