Мой обычный способ создания хеш-кода для произвольного набора хешируемых элементов:
int hash = 23;
hash = hash * 31 + item1Hash;
hash = hash * 31 + item2Hash;
hash = hash * 31 + item3Hash;
hash = hash * 31 + item4Hash;
hash = hash * 31 + item5Hash;
// etc
В вашем случае item1Hash
может быть просто a
, а item2Hash
может быть просто b
.
Значения 23 и 31 относительно не важны, если они простые (или, по крайней мере, взаимно простые).
Очевидно, что все еще будут столкновения, но вы не столкнетесь с обычными неприятными проблемами:
hash(a, a) == hash(b, b)
hash(a, b) == hash(b, a)
Если вы знаете больше о том, какими могут быть реальные значения a
и b
, вы, вероятно, сможете добиться большего, но это хорошая начальная реализация, которую легко запомнить и реализовать. Обратите внимание, что если есть вероятность, что вы соберете сборку с пометкой «проверка на арифметическое переполнение / недополнение», вы должны поместить все это в блок без контроля. (Переполнение подходит для этого алгоритма.)