10. 傅里叶变换

傅里叶变换用于分析各种滤波器的频率特性。对于图像,使用 2D 离散傅立叶变换 (DFT) 来查找频域。一种称为快速傅立叶变换 (FFT) 的快速算法用于计算 DFT。有关这些的详细信息可以在任何图像处理或信号处理教科书中找到。参考傅里叶变换

1. Numpy 中的傅立叶变换

首先,我们将看到如何使用 Numpy 找到傅立叶变换。 Numpy 有一个 FFT 包来做到这一点。 np.fft.fft2() 为我们提供了一个复杂数组的频率变换。它的第一个参数是输入图像,它是灰度的。第二个参数是可选的,它决定了输出数组的大小。如果它大于输入图像的大小,则在计算 FFT 之前用零填充输入图像。如果小于输入图像,输入图像将被裁剪。如果没有传递参数,输出数组大小将与输入相同。
现在一旦你得到结果,零频率分量(直流分量)将在左上角。如果要将其置于中心,则需要在两个方向上将结果移动 N/2。这只是由 函数 np.fft.fftshift() 完成的。 (更容易分析)。一旦找到频率变换,就可以找到幅度谱。

import cv2 as cv
import matplotlib.pyplot as plt
import numpy as np

img = cv.imread("../../file/photos/messi5.jpg", 0)
# gray = cv.cvtColor(img, cv.COLOR_BGR2GRAY)

f = np.fft.fft2(img)  # 实现傅里叶变换返回的是一个复数数组
fshift = np.fft.fftshift(f)  # 将零频率分量移动到频谱中心,图片默认在左上角

magnitude_spectrum = 20 * np.log(np.abs(fshift))  # 幅度_频谱 函数:20*np.log(np.abs(fshift))将经傅里叶变换的计算结果映射到[0,255]这个区间内。

# 画出对应图像
plt.subplot(121), plt.imshow(gray, 'gray'), plt.title("gray")
plt.axis("off")
plt.subplot(122), plt.imshow(magnitude_spectrum, 'gray'), plt.title("magnitude_spectrum")
plt.axis("off")

plt.show()

结果如下:
在这里插入图片描述
逆傅里叶变换:
所以你找到了频率变换 现在你可以在频域中做一些操作,比如高通滤波和重建图像,即找到逆 DFT。为此,这里使用大小为 20x20 的矩形窗口进行屏蔽即可去除低频。然后使用 np.fft.ifftshift() 应用反向移位,以便 DC 分量再次出现在左上角。然后使用 np.ifft2() 函数找到逆 FFT。结果同样是一个复数。您可以取其绝对值。

rows, cols = img.shape[:2]
crow, ccol = rows // 2, cols // 2
fshift[crow - 10:crow + 11, ccol - 10:ccol + 11] = 0
f_ishift = np.fft.ifftshift(fshift)  # 将频谱中心反向移位
img_back = np.fft.ifft2(f_ishift)  # 使用np.ifft2()函数找到逆FFT,得到复数数组
img_back = np.real(img_back)  # 取实数部分
plt.subplot(131), plt.imshow(gray, cmap='gray')
plt.title('Input Image'), plt.xticks([]), plt.yticks([])
plt.subplot(132), plt.imshow(img_back, cmap='gray')
plt.title('Image after HPF'), plt.xticks([]), plt.yticks([])
plt.subplot(133), plt.imshow(img_back)
plt.title('Result in JET'), plt.xticks([]), plt.yticks([])
plt.show()

结果如下:
在这里插入图片描述

2. OpenCV 中的傅里叶变换

OpenCV 为此提供了函数 cv.dft() cv.idft() 。它返回与之前相同的结果,但有两个通道。第一个通道将具有结果的实部,第二个通道将具有结果的虚部。输入图像应首先转换为 np.float32。以下将看到如何做到这一点。

img = cv.imread("../../file/photos/messi5.jpg")
gray = cv.cvtColor(img, cv.COLOR_BGR2GRAY)

dft = cv.dft(np.float32(gray), flags=cv.DFT_COMPLEX_OUTPUT)
dft_shift = np.fft.fftshift(dft)

magnitude_spectrum = 20 * np.log(cv.magnitude(dft_shift[:, :, 0], dft_shift[:, :, 1]))

plt.subplot(121), plt.imshow(gray, 'gray'), plt.title("Input Image")
plt.axis("off")

plt.subplot(122), plt.imshow(magnitude_spectrum, cmap="gray"), plt.title("magnitude_spectrum")
plt.axis("off")

plt.show()

Python:

magnitude	=	cv.magnitude(	x, y[, magnitude]	)

cv.magnitude()计算二维向量的大小。函数 cv::magnitude 计算由 x 和 y 数组的相应元素形成的二维向量的大小: d s t ( I ) = x ( I ) 2 + y ( I ) 2 dst(I)=\sqrt {x(I)^2+y(I)^2} dst(I)=x(I)2+y(I)2

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值