离散傅里叶变换

  • 作用:得到图像中几何结构信息
  • 结论:傅里叶变换后的白色部分(即幅度较大的低频部分),表示的是图像中慢变化的特性,或者说是灰度变化缓慢的特性(低频部分)。

    傅里叶变换后的黑色部分(即幅度低的高频部分),表示图像中快变化的特性,或者说是灰度变化快的特性(高频部分)。

dft()函数

函数原型

  1. void dft(InputArray src, OutputArray dst, int flage=0, int nonzeroRow=0)
  • InputArray 类型的src。输入矩阵,可以为实数或者虚数。
  • OutputArray 类型的dst。函数调用后的运算结果存在这里,其尺寸取决于标识符,也就是第三个参数。
  • int 类型的falgs。转换的标识符,有默认值0,取值可以为表中的结合。

标识符名称 | 意义

-|

DFT_INVERSE | 用一维或二维逆变换代替默认的正向变换。

DFT_SCALE | 缩放比例标识符,输出的结果都会以1/N进行放缩,通常擦很难过会结合DFT_INVERSE一起使用。

DFT_ROWS | 对输入矩阵的每行进行正向或反向的变换,此标识符可以在处理多种矢量的时候用于减小资源的开销,这些处理常常是三维或高位变换等复杂操作

DFT_COMPLEX_OUTPUT | 进行一维或二维复数苏胡祖反变换。这样的结果通常是一个大小相同的复矩阵。如果输入的矩阵有复数的共轭对称性(比如是一个带有DEF_COMPLEX_OUTPUT标识符的正变换结果),便会输出实矩阵。

  • int 类型的nonzeroRows,有默认值0.当此参数设为非零时(最好是取值为想要处理的那一行的值,比如C。rows),函数会假设只有输入矩阵的第一个非零行包含非零元素(没有设置DFT_INVERSE标识符),或只有输出矩阵的一个非零行包含非零元素(设置了DFT_INVERSE标识符)。这样的话,函数就可对其他行进行更高效的处理,以节省时间开销。

返回DFT最优尺寸大小:getOptimalDFTSize()函数

函数原型

  1. int getOptimalDFTSize(int vecsize)
  • int 类型的vecsize,向量尺寸,即图片的rows、cols。

扩充图像边界:copyMakeBorder()函数

函数原型

  1. void copyMakeBorder(InputArray src, OutputArray dst, int top, int bottom, int left, int right, int borderType, const Scalar& value=Scalar())
  • InputArray 类型的src,输入图像,即源图像,填Mat类型的对象即可。
  • OutputArray 类型的dst,函数调用后的运算结果存在这里,即这个参数用于存放函数调用后的输出结果,需和源图片有一样的尺寸和类型,且size 应该为Size(src.cols+left+right , src.rows+top+bottom)。
  • 接下来的4个参数分别是为int 类型的top、bottom、left、right,分别表示在源图像的四个方向上填充多少像素。
  • 第七个参数,int 类型的 borderType,边界类型,常见取值为BORDER_CONSTANT,可参考borderInterpolate()得到更多细节。
  • 第八个参数,const Scalar& 类型的value,有默认值Scalar(),可以理解为默认值为0。当borderType取值为BORDER_CONSTANT时,这个参数表示边界值。

计算二维矢量的幅值:magnitude()函数

函数原型

  1. void magnitude(InputArray x, InputArray y, OutputArray magnitude)
  • InputArray 类型的x,表示矢量的浮点型X坐标值,也就是实部。
  • InputArray 类型的y,表示矢量的浮点型Y坐标值,也就是虚部。
  • OutputArray 类型的magnitude,输出的幅值,它和第一个参数x有着同样的尺寸和类型。

计算自然对数:log()函数

计算数组元素绝对值的自然对数

函数原型

  1. void log(InputArray src, OutputArray dst)
  • 输入图像
  • 得到的对数值

矩阵归一化:normalize()函数

函数原型

  1. void normalize(InputArray src, OutputArray dst, double alpha=1, double beta=0, int norm_type=NORM_L2, int dtype=-1, InputArray mask=noArray())
  • InputArray 类型的src。输入图像,即源图像,填Mat类的对象即可。
  • OutputArray 类型的dst。函数调用后的运算结果。和源图片有一样的尺寸和类型。
  • double 类型的alpha。归一化后的最大值,默认值1。
  • double 类型的beta。归一化后的最小值,默认值0。
  • int类型的norm_type。归一化类型,有NORM_INF、NORM_L1、NORM_L2和NORM_MINMAX等参数可选,有默认值NORM_12。
  • int 类型的dtype,有默认值-1。当参数去负值时,输出矩阵和src有同样的类型,否则,它和src有同样的通道数,且此时图像深度为CV_MAT_DEPTH (dtype)。
  • InputArray 类型的mask,可选的操作掩膜,有默认值noArray()。

综合示例

  1. #include<core.hpp>
  2. #include<imgproc.hpp>
  3. #include<highgui.hpp>
  4. #include<iostream>
  5. using namespace cv;
  6. using namespace std;
  7. int main()
  8. {
  9. // 1.以灰度模式读取
  10. Mat srcImage = imread("..//..//0.jpg",0);
  11. if (!srcImage.data)
  12. {
  13. printf("读入错误");
  14. return false;
  15. }
  16. imshow("原始图像", srcImage);
  17. // 2.将输入图像延扩到最佳尺寸,边界用0补充
  18. int m = getOptimalDFTSize(srcImage.rows);
  19. int n = getOptimalDFTSize(srcImage.cols);
  20. // 将添加的像素初始化为0。
  21. Mat padded;
  22. copyMakeBorder(srcImage, padded, 0, m - srcImage.rows, 0, n - srcImage.cols, BORDER_CONSTANT, Scalar::all(0));
  23. // 3.为傅里叶变换的结果(实部和虚部)分配空间。
  24. // 将planes数组组合合并成一个多通道的数组complexI
  25. Mat planes[] = { Mat_<float>(padded), Mat::zeros(padded.size(),CV_32F) };
  26. Mat complexI;
  27. merge(planes, 2, complexI);
  28. // 4.进行离散傅里叶变换
  29. dft(complexI, complexI);
  30. // 5.将复数转换为幅值,即 log(1+sqrt(Re(DFT(I))^2 + Im(DFT(I))^2)
  31. split(complexI, planes); //将多通道数组complexI分离成几个单通道数组,[0]=Re,[1]=Im
  32. magnitude(planes[0], planes[1], planes[0]); //planes[0] = magnitude
  33. Mat magnitudeImage = planes[0];
  34. // 6.进行对数尺度(logarithmic scale)缩放
  35. magnitudeImage += Scalar::all(1);
  36. log(magnitudeImage, magnitudeImage); //求自然对数
  37. // 7.剪切和重分布幅度图象限
  38. //若有奇数行或奇数列,进行频谱裁剪
  39. magnitudeImage = magnitudeImage(Rect(0, 0, magnitudeImage.cols & -2, magnitudeImage.rows & -2));
  40. // 重新排列傅里叶图像中的象限,使得原点位于图像中心
  41. int cx = magnitudeImage.cols / 2;
  42. int cy = magnitudeImage.rows / 2;
  43. Mat q0(magnitudeImage, Rect(0, 0, cx, cy)); //ROI区域的左上
  44. Mat q1(magnitudeImage, Rect(cx, 0, cx, cy)); //ROI区域的右上
  45. Mat q2(magnitudeImage, Rect(0, cy, cx, cy)); //ROI区域的左下
  46. Mat q3(magnitudeImage, Rect(cx, cy, cx, cy)); //ROI区域的右下
  47. //交换象限(左上与右下进行交换)
  48. Mat tmp;
  49. q0.copyTo(tmp);
  50. q3.copyTo(q0);
  51. tmp.copyTo(q3);
  52. //交换象限(右上与左下进行交换)
  53. q1.copyTo(tmp);
  54. q2.copyTo(q1);
  55. tmp.copyTo(q2);
  56. // 8.归一化,用0到1之间的浮点值将矩阵变换为可视化的图像格式
  57. normalize(magnitudeImage, magnitudeImage, 0, 1, NORM_MINMAX);
  58. // 9.显示效果图
  59. imshow("频谱幅值", magnitudeImage);
  60. waitKey();
  61. return 0;
  62. }

OpenCV离散傅里叶变换的更多相关文章

  1. Opencv 实现图像的离散傅里叶变换(DFT)、卷积运算(相关滤波)

    我是做Tracking 的,对于速度要求非常高.发现傅里叶变换能够使用. 于是学习之. 核心: 最根本的一点就是将时域内的信号转移到频域里面.这样时域里的卷积能够转换为频域内的乘积! 在分析图像信号的 ...

  2. opencv 3 core组件进阶(3 离散傅里叶变换;输入输出XML和YAML文件)

    离散傅里叶变换 #include "opencv2/core/core.hpp" #include "opencv2/imgproc/imgproc.hpp" ...

  3. 离散傅里叶变换(DFT)

    目录     一.研究的意义     二.DFT的定义    三.DFT与傅里叶变换和Z变换的关系     四.DFT的周期性     五.matlab实验       五.1 程序         ...

  4. opencv3.2.0图像离散傅里叶变换

    源码: ##名称:离散傅里叶变换 ##平台:QT5.7.1+opencv3.2.0 ##日期:2017年12月13. /**** 新建QT控制台程序****/ #include <QCoreAp ...

  5. c语言数字图像处理(六):二维离散傅里叶变换

    基础知识 复数表示 C = R + jI 极坐标:C = |C|(cosθ + jsinθ) 欧拉公式:C = |C|ejθ 有关更多的时域与复频域的知识可以学习复变函数与积分变换,本篇文章只给出DF ...

  6. 五、c++实现离散傅里叶变换

    C++离散傅里叶变换 一.序言: 该教程基于之前的图像处理类MYCV,是对其的补充. 二.设计目标 对图像进行简单的离散傅里叶变换,并输出生成的频谱图. 三.需要提前掌握的知识 二维傅里叶变换公式: ...

  7. 用matlab脚本语言写M文件函数时用三种方法简单实现实现DFT(离散傅里叶变换)

    %用二重循环实现DFT: function xk=dt_0(xn); %define a function N=length(xn); %caculate the length of the vari ...

  8. 灰度图像--频域滤波 傅里叶变换之离散傅里叶变换(DFT)

    学习DIP第23天 转载请标明本文出处:http://blog.csdn.net/tonyshengtan,欢迎大家转载,发现博客被某些论坛转载后,图像无法正常显示,无法正常表达本人观点,对此表示很不 ...

  9. 【转】离散傅里叶变换-DFT(FFT)基础

    转:https://blog.csdn.net/zhangxz259/article/details/81627341 什么是离散傅里叶变换 matlab例子 本文是从最基础的知识开始讲解,力求用最通 ...

随机推荐

  1. python之路(内存,小数据池,编码等)

    代码块: python真正的代码块:一个模块,一个函数,一个类,一个文件等都是一个代码块. 但是,在python终端交互模式下,每一条代码都是一个代码块 python在同一个代码块中的变量,初始化对象 ...

  2. Android_ExpandableListView

    实现效果: 类似于QQ联系人列表 相关属性: android:childDivider:指定各组内子类表项之间的分隔条,图片不会完全显示, 分离子列表项的是一条直线 android:childIndi ...

  3. BLE直接Data channel抓包方法汇总

    之前一致在做一些有关与BLE安全研究的“基础设施建设”工作,我们知道,在BLE进入跳频之后,所有的固定标志都会消失,但是是不是意味着没办法了?不是的.我会提出一些恢复出来的方法. 首先,前导码分析,B ...

  4. 树莓派环境下使用python将h264格式的视频转为mp4

    个人博客 地址:https://www.wenhaofan.com/a/20190430144809 下载安装MP4Box 命令行下执行以下指令安装MP4Box   sudo apt-get inst ...

  5. 2级搭建类202-Oracle 18c SI ASM 静默搭建(OEL7.7)公开

    Oracle 18c 单实例 ASM UDEV 方式在 OEL 7.7 上的安装

  6. String类型的日期怎么转化为Date类型

    在一个SQL中,如果同时使用rownum和order by,会有一个先后顺序的问题. 比如select id1,id2 from t_tablename where rownum<3 order ...

  7. css3制作网页动画

    一.CSS3变形 CSS3变形是一些效果的集合 如平移.旋转.缩放.倾斜效果 每个效果都可以称为变形(transform),它们可以分别操控元素发生平移.旋转.缩放.倾斜等变化 二.CSS3位移:tr ...

  8. jQuery---淘宝精品案例

    淘宝精品案例 <!DOCTYPE html> <html> <head lang="en"> <meta charset="UT ...

  9. Leetcode Week1 Regular Expression Matching

    Question Given an input string (s) and a pattern (p), implement regular expression matching with sup ...

  10. Linux下用Bash语言实现输出最大值的功能

    题目链接: 题目描述 编写一个程序,输入a.b.c三个值,输出其中最大值. 输入 一行数组,分别为a b c 输出 a b c其中最大的数 样例输入 10 20 30 样例输出 30 复习下Linux ...