目标
我们将寻求以下问题的答案:
- 什么是傅里叶变换,为什么要使用它?
- 如何在OpenCV中做到这一点?
- 使用以下函数:copyMakeBorder() , merge() , dft() , getOptimalDFTSize() , log() 和 normalize****() 。
源代码 C++爪哇岛蟒
您可以从此处下载它,也可以在 OpenCV 源代码库中找到它。samples/cpp/tutorial_code/core/discrete_fourier_transform/discrete_fourier_transform.cpp
下面是 dft() 的用法示例:
#include “opencv2/core.hpp”
#include“opencv2/imgproc.hpp”
#include“opencv2/imgcodecs.hpp”
#include“opencv2/highgui.hpp”
#include < iostream>
使用命名空间 CV;
使用命名空间 std;
静态无效帮助(char ** argv)
{
cout << endl
<< “该程序演示了离散傅里叶变换(DFT)的使用。<< endl
<< “拍摄图像的 dft 并显示其功率谱。”<< endl << endl
<< “用法:” << endl
<< argv[0] << “ [image_name – default lena.jpg]” << endl << endl;
}
int main(int argc, char ** argv)
{
帮助(argv);
const char* 文件名 = argc >=2 ?argv[1] : “lena.jpg”;
席I = imread( samples::findFile( 文件名 ), IMREAD_GRAYSCALE);
if( I.空()){
cout << “打开图像时出错” << endl;
返回EXIT_FAILURE;
}
垫子衬垫;将输入图像放大到最佳大小
int m = getOptimalDFTSize( I.rows );
int n = getOptimalDFTSize( I.cols );在边框上添加零值
copyMakeBorder(I, 填充, 0, m - I.rows, 0, n - I.cols, BORDER_CONSTANT, 标量::all(0));
垫子平面[] = {Mat_(padded), Mat::zeros(padded.size()、CV_32F)};
垫复合物I;
merge(planes, 2, complexI);将另一个带有零的平面添加到展开的平面
dft(复合物I,复合物I);这样,结果可以适合源矩阵
计算幅度并切换到对数刻度
=> log(1 + sqrt(Re(DFT(I))^2 + Im(DFT(I))^2))
split(complexI, 平面);// planes[0] = Re(DFT(I), planes[1] = Im(DFT(I))
幅度(planes[0], planes[1], planes[0]);// planes[0] = magnitude
垫子 magI = 平面[0];
magI += 标量::all(1);切换到对数刻度
日志(magI, magI);
裁剪光谱,如果它有奇数行或列数
magI = magI(Rect(0, 0, magI.cols & -2, magI.行 & -2));
重新排列傅里叶图像的象限,使原点位于图像中心
int cx = magI。cols/2;
int cy = magI。行/2;
垫 q0(magI, Rect(0, 0, cx, cy));左上角 - 创建每个象限的投资回报率
垫 q1(magI, Rect(cx, 0, cx, cy));// 右上角
垫 q2(magI, Rect(0, cy, cx, cy));左下角
垫子 q3(magI, Rect(cx, cy, cx, cy));右下角
垫子tmp;交换象限(左上角和右下角)
问题0.copyTo(tmp);
q3.copyTo(q0);
TMP的。copyTo(q3);
q1.copyTo(tmp);交换象限(右上角和左下角)
q2.copyTo(q1);
TMP的。copyTo(q2);
归一化(magI, magI, 0, 1, NORM_MINMAX);将带有浮点值的矩阵转换为
可查看的图像形式(在值 0 和 1 之间浮动)。
imshow(“输入图像” , I );显示结果
imshow(“频谱幅度”, magI);
等待键();
返回EXIT_SUCCESS;
}
解释 C++爪哇岛蟒
傅里叶变换会将图像分解为正弦和余弦分量。换句话说,它将图像从其空间域转换为其频域。这个想法是,任何函数都可以用无限正弦和余弦函数的总和精确近似。傅里叶变换是一种如何做到这一点的方法。在数学上,二维图像傅里叶变换为:
F(k,l)=∑i=0N−1∑j=0N−1f(i,j)e−i2π(kiN+ljN)
e我x=COSX+ISINX
这里 f 是其空间域中的图像值,F 是其频域中的图像值。变换的结果是复数。可以通过真实图像和复杂图像或通过星等和相位图像来显示这一点。然而,在整个图像处理算法中,只有量级图像是有趣的,因为它包含我们需要的有关图像几何结构的所有信息。但是,如果您打算以这些形式对图像进行一些修改,然后需要重新转换它,则需要保留这两种形式。
在此示例中,我将演示如何计算和显示傅里叶变换的幅度图像。在数字图像的情况下是离散的。这意味着它们可能会占用给定域值中的值。例如,在基本灰度中,图像值通常介于 0 和 255 之间。因此,傅里叶变换也需要是离散类型,从而产生离散傅里叶变换 (DFT)。每当您需要从几何角度确定图像的结构时,您都需要使用它。以下是要遵循的步骤(如果是灰度输入图像 I):
将图像扩展到最佳大小
DFT 的性能取决于图像大小。对于数字 2、3 和 5 的倍数的图像大小,它往往是最快的。因此,为了实现最佳性能,通常最好将边框值填充到图像上,以获得具有此类特征的大小。getOptimalDFTSize() 返回这个最佳大小,我们可以使用 copyMakeBorder() 函数来扩展图像的边框(附加的像素初始化为零):
垫子衬垫;将输入图像放大到最佳大小
int m = getOptimalDFTSize( I.rows );
int n = getOptimalDFTSize( I.cols );在边框上添加零值
copyMakeBorder(I, 填充, 0, m - I.rows, 0, n - I.cols, BORDER_CONSTANT, Scalar::all(0));
为复杂和真实的价值腾出空间
傅里叶变换的结果很复杂。这意味着对于每个图像值,结果是两个图像值(每个组件一个)。此外,频域范围远大于其空间对应范围。因此,我们通常至少以浮点格式存储这些内容。因此,我们将输入图像转换为此类型,并使用另一个通道对其进行扩展以保存复数值:
垫子平面[] = {Mat_(padded), Mat::zeros(padded.size(), CV_32F)};
垫复合物I;
merge(planes, 2, complexI);将另一个带有零的平面添加到展开的平面
进行离散傅里叶变换
可以进行就地计算(输入与输出相同):
dft(复合物I,复合物I);这样,结果可以适合源矩阵
将实数值和复数值转换为量级
复数有一个实数 (Re) 和一个复数 (虚数 - Im) 部分。DFT 的结果是复数。DFT 的大小为:
M=Re(DFT(我))2+我m(DFT(我))2−−−−−−−−−−−−−−−−−−−−−−−−√2
转换为 OpenCV 代码:
split(complexI, 平面);// planes[0] = Re(DFT(I), planes[1] = Im(DFT(I))
幅度(planes[0], planes[1], planes[0]);// planes[0] = magnitude
垫子 magI = 平面[0];
切换到对数刻度
事实证明,傅里叶系数的动态范围太大,无法显示在屏幕上。我们有一些小的和一些高变化的值,我们不能像这样观察到。因此,高值将全部显示为白点,而小值将显示为黑点。为了使用灰度值进行可视化,我们可以将线性刻度转换为对数刻度:
M1=日志(1+M)
转换为 OpenCV 代码:
magI += 标量::all(1);切换到对数刻度
日志(magI, magI);
裁剪和重新排列
还记得,在第一步,我们扩展了图像吗?好吧,是时候扔掉新引入的价值观了。出于可视化目的,我们还可以重新排列结果的象限,使原点(零,零)与图像中心相对应。
裁剪光谱,如果它有奇数行或列数
magI = magI(Rect(0, 0, magI.cols & -2, magI.rows & -2));
重新排列傅里叶图像的象限,使原点位于图像中心
int cx = magI.cols/2;
int cy = magI.rows/2;
垫 q0(magI, Rect(0, 0, cx, cy));左上角 - 创建每个象限的投资回报率
垫 q1(magI, Rect(cx, 0, cx, cy));// 右上角
垫 q2(magI, Rect(0, cy, cx, cy));左下角
垫子 q3(magI, Rect(cx, cy, cx, cy));右下角
垫子tmp;交换象限(左上角和右下角)
q0.copyTo(tmp);
q3.copyTo(q0);
tmp.copyTo(q3);
q1.copyTo(tmp);交换象限(右上角和左下角)
q2.copyTo(q1);
tmp.copyTo(q2);
正常化
出于可视化目的,再次执行此操作。我们现在有了幅度,但这仍然超出了我们0到1的图像显示范围。我们使用 cv::normalize() 函数将我们的值归一化到这个范围。
归一化(magI, magI, 0, 1, NORM_MINMAX);将带有浮点值的矩阵转换为
可查看的图像形式(在值 0 和 1 之间浮动)。
结果
一个应用思路是确定图像中存在的几何方向。例如,让我们找出文本是否是水平的?看一些文本,你会注意到文本线也形成了水平线,字母形成了垂直线。在傅里叶变换的情况下,也可以看到文本片段的这两个主要组成部分。让我们使用这个关于文本的水平和旋转图像。
如果是水平文本:
如果是旋转文本:
您可以看到,频域中影响最大的分量(幅度图像上最亮的点)遵循图像上物体的几何旋转。由此,我们可以计算偏移量并执行图像旋转以纠正最终的未对齐。
如何学习大模型 AI ?
由于新岗位的生产效率,要优于被取代岗位的生产效率,所以实际上整个社会的生产效率是提升的。
但是具体到个人,只能说是:
“最先掌握AI的人,将会比较晚掌握AI的人有竞争优势”。
这句话,放在计算机、互联网、移动互联网的开局时期,都是一样的道理。
我在一线互联网企业工作十余年里,指导过不少同行后辈。帮助很多人得到了学习和成长。
我意识到有很多经验和知识值得分享给大家,也可以通过我们的能力和经验解答大家在人工智能学习中的很多困惑,所以在工作繁忙的情况下还是坚持各种整理和分享。但苦于知识传播途径有限,很多互联网行业朋友无法获得正确的资料得到学习提升,故此将并将重要的AI大模型资料包括AI大模型入门学习思维导图、精品AI大模型学习书籍手册、视频教程、实战学习等录播视频免费分享出来。
😝有需要的小伙伴,可以点击下方链接免费领取或者V扫描下方二维码免费领取🆓
第一阶段(10天):初阶应用
该阶段让大家对大模型 AI有一个最前沿的认识,对大模型 AI 的理解超过 95% 的人,可以在相关讨论时发表高级、不跟风、又接地气的见解,别人只会和 AI 聊天,而你能调教 AI,并能用代码将大模型和业务衔接。
- 大模型 AI 能干什么?
- 大模型是怎样获得「智能」的?
- 用好 AI 的核心心法
- 大模型应用业务架构
- 大模型应用技术架构
- 代码示例:向 GPT-3.5 灌入新知识
- 提示工程的意义和核心思想
- Prompt 典型构成
- 指令调优方法论
- 思维链和思维树
- Prompt 攻击和防范
- …
第二阶段(30天):高阶应用
该阶段我们正式进入大模型 AI 进阶实战学习,学会构造私有知识库,扩展 AI 的能力。快速开发一个完整的基于 agent 对话机器人。掌握功能最强的大模型开发框架,抓住最新的技术进展,适合 Python 和 JavaScript 程序员。
- 为什么要做 RAG
- 搭建一个简单的 ChatPDF
- 检索的基础概念
- 什么是向量表示(Embeddings)
- 向量数据库与向量检索
- 基于向量检索的 RAG
- 搭建 RAG 系统的扩展知识
- 混合检索与 RAG-Fusion 简介
- 向量模型本地部署
- …
第三阶段(30天):模型训练
恭喜你,如果学到这里,你基本可以找到一份大模型 AI相关的工作,自己也能训练 GPT 了!通过微调,训练自己的垂直大模型,能独立训练开源多模态大模型,掌握更多技术方案。
到此为止,大概2个月的时间。你已经成为了一名“AI小子”。那么你还想往下探索吗?
- 为什么要做 RAG
- 什么是模型
- 什么是模型训练
- 求解器 & 损失函数简介
- 小实验2:手写一个简单的神经网络并训练它
- 什么是训练/预训练/微调/轻量化微调
- Transformer结构简介
- 轻量化微调
- 实验数据集的构建
- …
第四阶段(20天):商业闭环
对全球大模型从性能、吞吐量、成本等方面有一定的认知,可以在云端和本地等多种环境下部署大模型,找到适合自己的项目/创业方向,做一名被 AI 武装的产品经理。
- 硬件选型
- 带你了解全球大模型
- 使用国产大模型服务
- 搭建 OpenAI 代理
- 热身:基于阿里云 PAI 部署 Stable Diffusion
- 在本地计算机运行大模型
- 大模型的私有化部署
- 基于 vLLM 部署大模型
- 案例:如何优雅地在阿里云私有部署开源大模型
- 部署一套开源 LLM 项目
- 内容安全
- 互联网信息服务算法备案
- …
学习是一个过程,只要学习就会有挑战。天道酬勤,你越努力,就会成为越优秀的自己。
如果你能在15天内完成所有的任务,那你堪称天才。然而,如果你能完成 60-70% 的内容,你就已经开始具备成为一名大模型 AI 的正确特征了。
这份完整版的大模型 AI 学习资料已经上传CSDN,朋友们如果需要可以微信扫描下方CSDN官方认证二维码免费领取【保证100%免费
】
😝有需要的小伙伴,可以Vx扫描下方二维码免费领取==🆓