opencv python 傅里葉變換的使用
理論
傅立葉變換用于分析各種濾波器的頻率特性,對于圖像,2D離散傅里葉變換(DFT)用于找到頻域.快速傅里葉變換(FFT)的快速算法用于計算DFT.
于一個正弦信號,x(t)=Asin(2πft),我們可以說 f 是信號的頻率,如果它的頻率域被接受,我們可以看到 f 的峰值.如果信號被采樣來形成一個離散信號,我們得到相同的頻率域,但是在[−π,π] or [0,2π]范圍內(nèi)是周期性的 (or [0,N] for N-point DFT).
可以將圖像視為在兩個方向上采樣的信號.因此,在X和Y方向上進行傅里葉變換可以得到圖像的頻率表示.
更直觀的是,對于正弦信號,如果振幅在短時間內(nèi)變化得非??欤憧梢哉f它是一個高頻信號.如果它變化緩慢,它是一個低頻信號,可以把同樣的想法擴展到圖片上,邊和噪聲是圖像中的高頻內(nèi)容,如果振幅沒有很大的變化,那就是低頻分量.
Numpy中的傅里葉變換
np.fft.fft2()
第一個參數(shù)是輸入圖像,它是灰度圖像
第二個參數(shù)是可選的,它決定了輸出數(shù)組的大小,如果它大于輸入圖像的大小,則輸入圖像在計算FFT之前填充了0.如果它小于輸入圖像,輸入圖像將被裁剪,如果沒有參數(shù)傳遞,輸出數(shù)組的大小將與輸入相同.
一旦得到結(jié)果,零頻率分量(DC分量)將位于左上角。 如果要將其置于中心位置,則需要在兩個方向上將結(jié)果移動N2.np.fft.fftshift()
,一旦你找到頻率變換,你就能找到大小譜.
代碼:
import cv2 import numpy as np from matplotlib import pyplot as plt img = cv2.imread('img.jpg',0) f = np.fft.fft2(img) fshift = np.fft.fftshift(f) magnitude_spectrum = 20*np.log(np.abs(fshift)) plt.subplot(121),plt.imshow(img, cmap = 'gray') plt.title('Input Image'), plt.xticks([]), plt.yticks([]) plt.subplot(122),plt.imshow(magnitude_spectrum, cmap = 'gray') plt.title('Magnitude Spectrum'), plt.xticks([]), plt.yticks([]) plt.show()
可以在中心看到更多的白色區(qū)域,表示低頻率的內(nèi)容更多.
現(xiàn)在可以在頻域做一些運算,比如高通濾波和重建圖像也就是找到逆DFT,只需用一個矩形窗口大小的60x60來移除低頻部分,使用np.fft.ifftshift()
應(yīng)用反向移動,使DC組件再次出現(xiàn)在左上角,然后使用np.ifft2()
函數(shù)找到反FFT,結(jié)果將會是一個復(fù)數(shù),可以取它的絕對值.
代碼:
import cv2 import numpy as np from matplotlib import pyplot as plt img = cv2.imread('img.jpg',0) f = np.fft.fft2(img) fshift = np.fft.fftshift(f) magnitude_spectrum = 20*np.log(np.abs(fshift)) rows, cols = img.shape crow,ccol = int(rows/2) , int(cols/2) fshift[crow-30:crow+30, ccol-30:ccol+30] = 0 f_ishift = np.fft.ifftshift(fshift) img_back = np.fft.ifft2(f_ishift) img_back = np.abs(img_back) plt.subplot(221),plt.imshow(img, cmap = 'gray') plt.title('Input Image'), plt.xticks([]), plt.yticks([]) plt.subplot(222),plt.imshow(magnitude_spectrum, cmap = 'gray') plt.title('Magnitude Spectrum'), plt.xticks([]), plt.yticks([]) plt.subplot(223),plt.imshow(img_back) plt.title('Result in JET'), plt.xticks([]), plt.yticks([]) plt.subplot(224),plt.imshow(img_back, cmap = 'gray') plt.title('Image after HPF'), plt.xticks([]), plt.yticks([]) plt.show()
結(jié)果表明,高通濾波是一種邊緣檢測操作.
OpenCV中的傅里葉變換
OpenCV提供了cv.dft()
和cv.idft()
函數(shù).它返回與前面相同的結(jié)果,但是有兩個通道.第一個通道將會有結(jié)果的實部,第二個通道將會有一個虛部.
輸入圖像首先應(yīng)該轉(zhuǎn)換為np.float32
import cv2 import numpy as np from matplotlib import pyplot as plt img = cv2.imread('img.jpg',0) dft = cv2.dft(np.float32(img),flags = cv2.DFT_COMPLEX_OUTPUT) dft_shift = np.fft.fftshift(dft) magnitude_spectrum = 20*np.log(cv2.magnitude(dft_shift[:,:,0],dft_shift[:,:,1])) plt.subplot(121),plt.imshow(img, cmap = 'gray') plt.title('Input Image'), plt.xticks([]), plt.yticks([]) plt.subplot(122),plt.imshow(magnitude_spectrum, cmap = 'gray') plt.title('Magnitude Spectrum'), plt.xticks([]), plt.yticks([]) plt.show()
也可以使用cv.cartToPolar()
,它可以在一次拍攝中同時返回大小和相位.
現(xiàn)在我們要做的是逆DFT.這次我們將移除圖像中的高頻內(nèi)容,即我們將LPF應(yīng)用到圖像中.它實際上模糊了圖像.為此,我們先創(chuàng)建一個具有高值(1)低頻率的掩模,即我們通過低頻內(nèi)容,而在高頻區(qū)域則是0。
import cv2 import numpy as np from matplotlib import pyplot as plt img = cv2.imread('img.jpg',0) dft = cv2.dft(np.float32(img),flags = cv2.DFT_COMPLEX_OUTPUT) dft_shift = np.fft.fftshift(dft) rows, cols = img.shape crow,ccol = int(rows/2) , int(cols/2) # create a mask first, center square is 1, remaining all zeros mask = np.zeros((rows,cols,2),np.uint8) mask[crow-30:crow+30, ccol-30:ccol+30] = 1 # apply mask and inverse DFT fshift = dft_shift*mask f_ishift = np.fft.ifftshift(fshift) img_back = cv2.idft(f_ishift) img_back = cv2.magnitude(img_back[:,:,0],img_back[:,:,1]) plt.subplot(121),plt.imshow(img, cmap = 'gray') plt.title('Input Image'), plt.xticks([]), plt.yticks([]) plt.subplot(122),plt.imshow(img_back, cmap = 'gray') plt.title('Magnitude Spectrum'), plt.xticks([]), plt.yticks([]) plt.show()
NOTE:
OpenCV函數(shù)cv.dft()
和cv.idft()
比Numpy函數(shù)更快.但是Numpy功能更加用戶友好.
以上就是本文的全部內(nèi)容,希望對大家的學(xué)習(xí)有所幫助,也希望大家多多支持腳本之家。
相關(guān)文章
Python數(shù)字圖像處理代數(shù)之加減乘運算
這篇文章主要介紹了Python數(shù)字圖像處理代數(shù)運算,對其中的加、減、乘運算分別作了詳細的講解,有需要的朋友可以借鑒參考下,希望能夠有所幫助2021-09-09python中matplotlib調(diào)整圖例位置的方法實例
在matplotlib中,一般圖例默認是在圖表內(nèi)部的,如果要放置到圖例外面,需要對坐標(biāo)進行指定,下面這篇文章主要給大家介紹了關(guān)于python中matplotlib調(diào)整圖例位置的相關(guān)資料,需要的朋友可以參考下2022-06-06Python實現(xiàn)計算字符串中出現(xiàn)次數(shù)最多的字符示例
這篇文章主要介紹了Python實現(xiàn)計算字符串中出現(xiàn)次數(shù)最多的字符,涉及Python針對字符串的遍歷、統(tǒng)計等相關(guān)操作技巧,需要的朋友可以參考下2019-01-01pycharm運行和調(diào)試不顯示結(jié)果的解決方法
今天小編就為大家分享一篇pycharm運行和調(diào)試不顯示結(jié)果的解決方法,具有很好的參考價值,希望對大家有所幫助。一起跟隨小編過來看看吧2018-11-11Python PyQt5實戰(zhàn)項目之文件拷貝器的具體實現(xiàn)詳解
PyQt5以一套Python模塊的形式來實現(xiàn)功能。它包含了超過620個類,600個方法和函數(shù)。本篇文章手把手帶你用PyQt5實現(xiàn)一個簡單的文件拷貝器,大家可以在過程中查缺補漏,提升水平2021-11-11python?apscheduler?cron定時任務(wù)觸發(fā)接口自動化巡檢過程
這篇文章主要介紹了python?apscheduler?cron定時任務(wù)觸發(fā)接口自動化巡檢過程,具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教2023-03-03