Для моего приложения мне нужно обрабатывать кучу объектов (скажем, int
s), которые впоследствии разделяются и сортируются на более мелкие. ведра. С этой целью я храню элементы в одном непрерывном массиве
arr = {0,1,2,3,4,5,6,7,8,9,10,11,12,13,14...}
, а информация о сегментах (подсписках) задается смещениями к первому элементу в соответствующем сегменте и длинами подсписка.
Так, например, данное
offsets = {0,3,8,..}
sublist_lengths = {3,5,2,...}
приведет к следующим разбиениям:
0 1 2 || 3 4 5 6 7 || 8 9 || ...
Я ищу несколько общий и эффективный способ запуска алгоритмов, таких как сокращения, в сегментах только с использованием собственных ядер или библиотека
. Суммирование сегментов должно дать:
3 || 25 || 17 || ...
То, что я придумал:
вариант 1 : пользовательские ядра требуют довольно небольшой обработки, копий в общую память, правильного выбора размеров блока и сетки и собственная реализация алгоритмов, таких как сканирование, сокращение и т. д. Кроме того, для каждой отдельной операции потребуется собственное настраиваемое ядро. В общем, мне ясно, как это сделать, но после использования тяги
в течение последних двух дней у меня сложилось впечатление, что может быть более умный способ
вариант 2 : генерировать массив ключей из смещений ( {0,0,0,1,1,1,1,1,2,2,3, ...}
в приведенном выше примере) и использовать thust :: reduce_by_key
. Однако мне не нравится создание дополнительных списков.
вариант 3 : Используйте thust :: transform_iterator
вместе с thrust :: counting_iterator
, чтобы на лету сгенерировать указанный выше список ключей. К сожалению, я не могу придумать реализацию, которая не требует приращения индексов в списке смещений на устройстве и исключает параллелизм.
Каким будет наиболее разумный способ реализовать это?