Я ищу для вычисления энтропии и взаимной информации огромное количество раз в критическом по производительности коде. В качестве промежуточного шага мне нужно подсчитать количество вхождений каждого значения. Например:Самый эффективный способ подсчета случаев?
uint[] myArray = [1,1,2,1,4,5,2];
uint[] occurrences = countOccurrences(myArray);
// Occurrences == [3, 2, 1, 1] or some permutation of that.
// 3 occurrences of 1, 2 occurrences of 2, one each of 4 and 5.
Конечно очевидные способы, чтобы сделать это, либо с помощью ассоциативного массива или путем сортировки массива входного сигнала с помощью «стандартный» алгоритм сортировки как быстрой сортировки. Для небольших целых чисел, таких как байты, этот код в настоящее время специализируется на использовании простого старого массива.
Есть ли какой-нибудь умный алгоритм для этого более эффективно, чем хеш-таблица или «стандартный» алгоритм сортировки, такой как реализация ассоциативного массива, которая в значительной степени способствует обновлениям над вставками или алгоритму сортировки, который сияет, когда ваши данные имеют много связей?
Примечание. Неразрешенные целые числа являются всего лишь одним из примеров возможного типа данных. Я ищу для реализации разумно общего решения здесь, хотя, поскольку целые числа и структуры, содержащие только целые числа, являются обычными случаями, меня бы интересовали решения, специфичные для них, если они чрезвычайно эффективны.
Не знаю, как вы сказали выше. Сортируйте массив, а затем последовательно пройдите его в проходе. –
Возможно, вы могли бы использовать какой-то Hadoop или Map/Reduce для ускорения вашего алгоритма? Помимо этого я ничего не вижу. – kgrad
@kgrad: Я уже полностью использую все свои ядра, распараллеливая внешний цикл, поэтому не было бы распараллеливания отдельного выполнения этой функции. – dsimcha