Я пытаюсь реализовать алгоритм обнаружения переднего плана кодовой книги, описанный здесь в книге Обучение OpenCV .
Алгоритм описывает только подход, основанный на кодовой книге, для каждого пикселя изображения. Поэтому я выбрал самый простой подход - иметь массив кодовых книг, по одной на каждый пиксель, очень похожий на матричную структуру, лежащую в основе IplImage. Длина массива равна количеству пикселей на изображении.
Я написал следующие два цикла для изучения фона и сегментирования переднего плана. Он использует мое ограниченное понимание структуры матрицы внутри изображения src и использует арифметику указателей для прохождения пикселей.
void foreground(IplImage* src, IplImage* dst, codeBook* c, int* minMod, int* maxMod){
int height = src->height;
int width = src->width;
uchar* srcCurrent = (uchar*) src->imageData;
uchar* srcRowHead = srcCurrent;
int srcChannels = src->nChannels;
int srcRowWidth = src->widthStep;
uchar* dstCurrent = (uchar*) dst->imageData;
uchar* dstRowHead = dstCurrent;
// dst has 1 channel
int dstRowWidth = dst->widthStep;
for(int row = 0; row < height; row++){
for(int column = 0; column < width; column++){
(*dstCurrent) = find_foreground(srcCurrent, (*c), srcChannels, minMod, maxMod);
dstCurrent++;
c++;
srcCurrent += srcChannels;
}
srcCurrent = srcRowHead + srcRowWidth;
srcRowHead = srcCurrent;
dstCurrent = dstRowHead + dstRowWidth;
dstRowHead = dstCurrent;
}
}
void background(IplImage* src, codeBook* c, unsigned* learnBounds){
int height = src->height;
int width = src->width;
uchar* srcCurrent = (uchar*) src->imageData;
uchar* srcRowHead = srcCurrent;
int srcChannels = src->nChannels;
int srcRowWidth = src->widthStep;
for(int row = 0; row < height; row++){
for(int column = 0; column < width; column++){
update_codebook(srcCurrent, c[row*column], learnBounds, srcChannels);
srcCurrent += srcChannels;
}
srcCurrent = srcRowHead + srcRowWidth;
srcRowHead = srcCurrent;
}
}
Программа работает, но очень вяло. Есть ли что-то очевидное, что замедляет это? Или это врожденная проблема простой реализации? Что я могу сделать, чтобы ускорить это? Каждая кодовая книга сортируется в определенном порядке, поэтому для обработки каждого пикселя требуется линейное время. Поэтому удваивайте фоновые выборки, и программа работает медленнее на 2 для каждого пикселя, который затем увеличивается на количество пикселей. Но с точки зрения реализации я не вижу четкого, логичного способа сортировки записей элемента кода.
Мне известно, что в примерах opencv приведен пример реализации того же алгоритма. Однако эта структура кажется гораздо более сложной. Я хочу больше понять причины этого метода, я знаю, что могу просто изменить образец для реальных приложений.
Спасибо