這篇文章給大家分享的是有關Python OpenCV如何實現圖像傅里葉變換的內容。小編覺得挺實用的,因此分享給大家做個參考,一起跟隨小編過來看看吧。
對于二維圖像處理,通常使用 x , y x, yx,y 表示離散的空間域坐標變量,用 u , v u,vu,v 表示離散的頻率域變量。二維離散傅里葉變換(DFT)和反變換(IDFT)為:
二維離散傅里葉變換也可以用極坐標表示:
傅里葉頻譜(Fourier spectrum)為:
傅里葉相位譜(Fourier phase spectrum)為:
傅里葉功率譜(Fourier power spectrum)為:
空間取樣和頻率間隔是相互對應的,頻率域所對應的離散變量間的間隔為:Δu=1/MΔT, Δυ=1/NΔZ。即:頻域中樣本之間的間隔,與空間樣本之間的間隔及樣本數量的乘積成反比。
空間域濾波器和頻率域濾波器也是相互對應的,二維卷積定理是在空間域和頻率域濾波之間建立等價關系的紐帶:
這表明 F 和 H 分別是 f 和 h 的傅里葉變換;f 和 h 的空間卷積的傅里葉變換,是它們的變換的乘積。
使用 OpenCV 中的 cv.dft() 函數也可以實現圖像的傅里葉變換,cv.idft() 函數實現圖像傅里葉逆變換。
函數說明:
cv.dft(src[, dst[, flags[, nonzeroRows]]]) → dst cv.idft(src[, dst[, flags[, nonzeroRows]]]) → dst
參數說明:
src:輸入圖像,單通道灰度圖像,使用 np.float32 格式
dst:輸出圖像,圖像大小與 src 相同,數據類型由 flag 決定
flag:轉換標識符
cv.DFT_INVERSE:用一維或二維逆變換取代默認的正向變換
cv.DFT_SCALE:縮放比例標識,根據元素數量求出縮放結果,常與DFT_INVERSE搭配使用
cv.DFT_ROWS: 對輸入矩陣的每行進行正向或反向的傅里葉變換,常用于三維或高維變換等復雜操作
cv.DFT_COMPLEX_OUTPUT:對一維或二維實數數組進行正向變換,默認方法,結果是由 2個通道表示的復數陣列,第一通道是實數部分,第二通道是虛數部分
cv.DFT_REAL_OUTPUT:對一維或二維復數數組進行逆變換,結果通常是一個尺寸相同的復數矩陣
注意事項:
1.輸入圖像 src 是 np.float32 格式,如圖像使用 np.uint8 格式則必須先轉換 np.float32 格式。
2.默認方法 cv.DFT_COMPLEX_OUTPUT 時,輸入 src 是 np.float32 格式的單通道二維數組,輸出 dst 是 2個通道的二維數組,第一通道 dft[:,:,0] 是實數部分,第二通道 dft[:,:,1] 是虛數部分。
3.不能直接用于顯示圖像??梢允褂?cv.magnitude() 函數將傅里葉變換的結果轉換到灰度 [0,255]。
4.idft(src, dst, flags) 等價于 dft(src, dst, flags=DFT_INVERSE)。
5.OpenCV 實現傅里葉變換,計算速度比 Numpy 更快。
轉換標識符為 cv.DFT_COMPLEX_OUTPUT 時,cv.dft() 函數的輸出是 2個通道的二維數組,使用 cv.magnitude() 函數可以實現計算二維矢量的幅值 。
函數說明:
cv.magnitude(x, y[, magnitude]) → dst
參數說明:
x:一維或多維數組,也表示復數的實部,浮點型
y:一維或多維數組,也表示復數的虛部,浮點型,數組大小必須與 x 相同
dst:輸出數組,數組大小和數據類型與 x 相同,運算公式為:
傅里葉變換及相關操作的取值范圍可能不適于圖像顯示,需要進行歸一化處理。 OpenCV 中的 cv.normalize() 函數可以實現圖像的歸一化。
函數說明:
cv.normalize(src, dst[, alpha[, beta[, norm_type[, dtype[, mask]]]]]) → dst
參數說明:
src:輸入圖像
dst:輸出結果,與輸入圖像同尺寸同類型
alpha:歸一化后的最小值,可選項,默認值為0
beta:歸一化后的最大值,可選項,默認值為1
norm_type:歸一化類型
NORM_INF:Linf 范數(絕對值的最大值)
NORM_L1:L1 范數(絕對值的和)
NORM_L2:L2 范數(歐幾里德距離),默認類型
NORM_MINMAX:線性縮放,常用類型
dtype:可選項,默認值 -1,表示輸出矩陣與輸入圖像類型相同
mask:掩模遮罩,可選項,默認無遮罩
傅里葉變換在理論上需要O(MN)²次運算,非常耗時;快速傅里葉變換只需要O(MN㏒(MN)) 次運算就可以完成。
OpenCV 中的傅里葉變換函數 cv.dft() 對于行數和列數都可以分解為2^p*3^q*5^r的矩陣的計算性能最好。為了提高運算性能,可以對原矩陣的右側和下方補 0,以滿足該分解條件。OpenCV 中的 cv.getOptimalDFTSize() 函數可以實現圖像的最優 DFT 尺寸擴充,適用于 cv.dft() 和 np.fft.fft2()。
函數說明:
cv.getOptimalDFTSize(versize) → retval
參數說明:
versize:數組大小
retval:DFT 擴充的最優數組大小
# 8.11:OpenCV 實現二維圖像的離散傅里葉變換 imgGray = cv2.imread("../images/Fig0424a.tif", flags=0) # flags=0 讀取為灰度圖像 # cv2.dft 實現圖像的傅里葉變換 imgFloat32 = np.float32(imgGray) # 將圖像轉換成 float32 dft = cv2.dft(imgFloat32, flags=cv2.DFT_COMPLEX_OUTPUT) # 傅里葉變換 dftShift = np.fft.fftshift(dft) # 將低頻分量移動到頻域圖像的中心 # 幅度譜 # ampSpe = np.sqrt(np.power(dft[:,:,0], 2) + np.power(dftShift[:,:,1], 2)) dftAmp = cv2.magnitude(dft[:,:,0], dft[:,:,1]) # 幅度譜,未中心化 dftShiftAmp = cv2.magnitude(dftShift[:,:,0], dftShift[:,:,1]) # 幅度譜,中心化 dftAmpLog = np.log(1 + dftShiftAmp) # 幅度譜對數變換,以便于顯示 # 相位譜 phase = np.arctan2(dftShift[:,:,1], dftShift[:,:,0]) # 計算相位角(弧度制) dftPhi = phase / np.pi*180 # 將相位角轉換為 [-180, 180] print("dftMag max={}, min={}".format(dftAmp.max(), dftAmp.min())) print("dftPhi max={}, min={}".format(dftPhi.max(), dftPhi.min())) print("dftAmpLog max={}, min={}".format(dftAmpLog.max(), dftAmpLog.min())) # cv2.idft 實現圖像的逆傅里葉變換 invShift = np.fft.ifftshift(dftShift) # 將低頻逆轉換回圖像四角 imgIdft = cv2.idft(invShift) # 逆傅里葉變換 imgRebuild = cv2.magnitude(imgIdft[:,:,0], imgIdft[:,:,1]) # 重建圖像 plt.figure(figsize=(9, 6)) plt.subplot(231), plt.title("Original image"), plt.axis('off') plt.imshow(imgGray, cmap='gray') plt.subplot(232), plt.title("DFT Phase"), plt.axis('off') plt.imshow(dftPhi, cmap='gray') plt.subplot(233), plt.title("Rebuild image with IDFT"), plt.axis('off') plt.imshow(imgRebuild, cmap='gray') plt.subplot(234), plt.title("DFT amplitude spectrum"), plt.axis('off') plt.imshow(dftAmp, cmap='gray') plt.subplot(235), plt.title("DFT-shift amplitude"), plt.axis('off') plt.imshow(dftShiftAmp, cmap='gray') plt.subplot(236), plt.title("Log-trans of DFT amp"), plt.axis('off') plt.imshow(dftAmpLog, cmap='gray') plt.tight_layout() plt.show()
感謝各位的閱讀!關于“Python OpenCV如何實現圖像傅里葉變換”這篇文章就分享到這里了,希望以上內容可以對大家有一定的幫助,讓大家可以學到更多知識,如果覺得文章不錯,可以把它分享出去讓更多的人看到吧!
免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。