opencv 图片的离散傅里叶变换DFT

本文介绍如何使用OpenCV的copyMakeBorder函数扩展图像边界,并通过DFT进行频谱分析。具体步骤包括图像边界扩展、傅里叶变换、频谱调整及显示等。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

copyMakeBorder(InuptArray src, OutputArray dst, int top , int bottom, int left, int right, int borderType, const Scalar& value=Scalar())  

该函数是用来扩展一个图像的边界

src: 源图像

dst: 目标图像,和源图像有相同的类型

top:表示在上边界扩展多少像素

bottom:表示在下边界扩展多少像素

left:表示在左边界扩展多少像素

right: 表示在右边界扩展多少像素

borderType: 边框类型

value: 当borderType==BORDER_CONSTANT时需要指定该值。

merge()函数是把多个但通道数组连接成1个多通道数组,而split()函数则相反,把1个多通道函数分解成多个但通道函数

#include<iostream>
#include<opencv2\opencv.hpp>
using namespace std;
using namespace cv;

int main(int argc, int **argv) {
	Mat src, dst;
	src = imread("F:\\img\\game02.jpg",0);
	dst = Mat::zeros(src.size(), src.type());
	if (!src.data) {
		cout << "src image open failed !" << endl;
	}
	//得到扩展图像的最佳尺寸,当图像的尺寸为2,3,5的整数倍时,计算速度最快
	int m = getOptimalDFTSize(src.rows);
	int n = getOptimalDFTSize(src.cols);
	Mat padded;
	//对图像边界进行扩充
	copyMakeBorder(src, padded, 0, m - src.rows, 0, n - src.cols, BORDER_CONSTANT, Scalar::all(0));
	//为傅里叶变换结果(实部和虚部)分配存储空间
	Mat plane[] = {Mat_<float>(padded),Mat::zeros(padded.size(),CV_32F)};
	Mat complexI;
	merge(plane, 2,complexI);
	//傅里叶变换
	dft(complexI, complexI);
	//将复数转换为幅值
	split(complexI,plane);
	Mat magnitudeImg;
	magnitude(plane[0],plane[1],plane[0]);
	magnitudeImg = plane[0];
	//进行对数尺度缩放
	magnitudeImg += Scalar::all(1);
	log(magnitudeImg, magnitudeImg);

	//重新分布图像的象限
	//若有奇数列或奇数行,进行频谱裁剪
	magnitudeImg = magnitudeImg(Rect(0, 0, magnitudeImg.cols &-2, magnitudeImg.rows &-2));
	//计算图像的中心
	int cx = magnitudeImg.cols / 2;
	int cy = magnitudeImg.rows / 2;

	Mat p0(magnitudeImg,Rect(0, 0, cx, cy));	//ROI左上
	Mat p1(magnitudeImg,Rect(cx, 0, cx, cy));	//ROI右上
	Mat p2(magnitudeImg,Rect(0, cy, cx, cy));	//ROI左下
	Mat p3(magnitudeImg,Rect(cx, cy, cx, cy));	//ROI右下

	//左上和右下进行交换
	Mat temp1;
	p0.copyTo(temp1);
	p3.copyTo(p0);
	temp1.copyTo(p3);

	//右上和左下进行交换
	Mat temp2;
	p1.copyTo(temp2);
	p2.copyTo(p1);
	temp2.copyTo(p2);
	//归一化
	normalize(magnitudeImg, magnitudeImg, 0, 1, NORM_MINMAX);
	imshow("原图", src);
	imshow("DFT幅值", magnitudeImg);
	waitKey(0);

	return 0;
}

结果:



评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值