В настоящее время я пишу программу, которая выделяет 2D-блоки большого 2D-массива и помещает их в меньший 2D-массив. Массивы фактически сохраняются как массивы 1D, но я предполагаю, что они представляют собой 2D-массивы, которые выпрямляются. Прямо сейчас для циклов убедитесь, что я вынимаю Nx, Ny элементов большой петли, прежде чем переходить к новой части большого массива.Unwrapping 3 C++ loops in cuda
Я не могу найти способ сделать это более эффективно в ядре CUDA. Я мог бы сделать решение, если бы имел только массивы одинакового размера. Но с новым местоположением после каждого элемента Nx * Ny я запутался.
Ниже приведены три петли, которые заставляют все это происходить. posx и posy содержат координаты, которые должны быть вычтены стартовыми позициями.
for (int i = 0; i < loadsize; i++)
{
for (int k = 0; k < Searchsizey; k++)
{
for (int l = 0; l < Searchsizex; l++)
{
img[count] = ImgInt[posx[i] - ImgStartx + (posy[i] - ImgStarty) * sizex + sizex*k + l];
count++;
}
}
}
Проблема в том, что две внутренние петли работают максимально до Searchsizex и Searchseyey. Если я должен реализовать это в ядре с использованием l и k в качестве индексации из потоков, они станут больше, чем Searchsizex и Searchsizey.
Я думал о создании ядра CUDA, которое выполняет итерацию корыта i, но он действительно кажется очень эффективным для этого. Ниже я расскажу о том, как включить ядро, но мне это не очень нравится. Его единственный вид «полупараллельный».
Упование вы имеете некоторые предложения для как сделать эту параллель, спасибо!
int l = blockIdx.x*blockDim.x + threadIdx.x;
int k = blockIdx.y*blockDim.y + threadIdx.y;
for (int i = 0; i < loadsize; i++){
img[l + k*sizex + (i*sizex*sizey)] = ImgInt[posx[i] - ImgStartx + (posy[i] - ImgStarty) * sizex + sizex*k + l];
}
В зависимости от размеров вашего ввода и величины posx и posy могут подойти различные подходы. Не могли бы вы предоставить приблизительные показатели для них? Также тип данных img? –
posx и posy могут варьироваться от 0 до 1000 и там размер loadzie может составлять сотни. Img - это float – LukaK
Чтобы получить максимальную производительность, вы хотите использовать float4 как записи и в зависимости от целевого оборудования, используйте текстуру или поверхность для ImgInt. В остальном ваш подход к параллелизму кажется очень разумным. –