Размытие матрицы с помощью быстрого преобразования Фурье

Я хочу размыть значения в матрице, чтобы в соседних элементах не было резких переходов.

На странице Википедии Размытие по Гауссу я нашел некоторую информацию о размытии по Гауссу. Я пробовал это с самым простым алгоритмом, и, следовательно, время выполнения было слишком большим. Честно говоря, я не уверен, что моя реализация правильная, так как на граничных тайлах резкий переход все еще существует.

Я заметил, что это размытие можно сделать с помощью дискретных преобразований Фурье, которые намного быстрее, но я не мог этого понять.

Итак, идея состоит в том, что мы можем получить размытую матрицу с помощью следующих формул:

blurredMatrix = IFFT[FFT[initialMatrix]FFT[weightingFunction]]

Где FFT/IFFT — это быстрое преобразование Фурье/обратное быстрое преобразование Фурье.

В настоящее время я пытаюсь провести некоторое тестирование Wolfram Mathematica, чтобы убедиться, что такое приближение с преобразованиями Фурье верно.

Я использую GaussianMatrix в качестве функции взвешивания.

Мне нужно двумерное размытие, поэтому я создал матрицу Гаусса, как показано ниже:

Предположим, наша исходная матрица имеет размеры nxn, где n = 2k+1

G = Chop[GaussianMatrix[k] GaussianMatrix[k], 10^6]

Затем я попытался создать blurredMatrix, как показано ниже:

blurredMatrix = Chop[FourierDCT[(FourierDCT[G]) (FourierDCT[initialMatrix]), 3], 10^-6]

Но в результате получаю нули.

Кажется, я все делаю неправильно.

Кроме того, я пробовал другой подход:

f[xi_, yj_] := 1/(2 \[Pi] \[Sigma]^2) Exp[-(((xi^2) + (yj^2) )/(2 \[Sigma]^2))];<br/>
[Sigma] = 3;<br/>
G = Chop[N[Table[f[i, j], {i, 1, 100}, {j, 1, 100}]]]; <br/>
Tavg = Chop[ 1000 InverseFourier[(Fourier[G]) (Fourier[T]) ], 10^-6]; <br/>

При таком подходе картинка выглядит нормально (изображение размыто), но есть большая разница между значениями blurredMatrix и initialMatrix.

Кажется, есть некоторая нормализация или другие проблемы.

Мне нужно написать код на C/C++, есть библиотека FFTW на C, которая поддерживает дискретные преобразования Фурье.

Пожалуйста, дайте мне знать, если это неправильный способ размытия, и есть ли другие возможности делать то, что я хочу.


person Heghine    schedule 21.05.2015    source источник
comment
Использование БПФ для выполнения сверток эффективно только при наличии очень больших ядер свертки. В большинстве приложений размытия ядро ​​намного меньше изображения, поэтому БПФ будет значительно медленнее. Какого размера ваше желаемое ядро ​​размытия?   -  person Adi Shavit    schedule 21.05.2015
comment
@AdiShavit, я использую ядро ​​​​3x3, но размер ядра контролируется переменной окружения. Я нашел несколько статей в Интернете, чтобы ускорить размытие по Гауссу, но я не уверен, что это правильный путь. Также мне нужно применить размытие на огромном количестве матриц.   -  person Heghine    schedule 21.05.2015
comment
Если у вас есть доступ к видеокарте, вы можете выполнить свертки с помощью CUDA. Оказывается, видеокарты действительно эффективны при выполнении больших матричных вычислений.   -  person jakebower    schedule 21.05.2015
comment
Пробовал редактировать предыдущую, но слишком медленно. Я нашел учебник по концепции. Нашел учебник по концепции: developer.download.nvidia.com/assets /cuda/files/ Как уже сказали эти ребята, nVidia также рекомендует не использовать подход FFT для этого размера ядра.   -  person jakebower    schedule 21.05.2015


Ответы (1)


Использование БПФ для выполнения сверток эффективно только при наличии очень больших ядер свертки. В большинстве приложений размытия ядро ​​​​намного меньше изображения, например. 3x3, поэтому БПФ будет значительно медленнее.

Существует множество реализаций сверток с малым ядром.
Большинство современных аппаратных средств поддерживает такие встроенные операции (MMX, SSE, графические процессоры...).
В вашем случае БПФ, вероятно, не подходит.

В C++ OpenCV поддерживает как кросс-платформенное, так и аппаратное ускорение свертки изображений. Свертки действительно являются одной из (если не) наиболее фундаментальной операцией любого пакета обработки изображений и сигналов.

person Adi Shavit    schedule 21.05.2015
comment
Не могли бы вы поделиться ссылками на реализации? - person Heghine; 21.05.2015
comment
Я добавил ссылку на OpenCV, но ничего не зная о вашей платформе и среде, трудно дать что-то конкретное. Я уверен, что поиск в Интернете даст десятки вариантов для большинства платформ. - person Adi Shavit; 21.05.2015