首页 > 编程语言 >OPenCV高级编程——OpenCV常见的API及绘图知识详解

OPenCV高级编程——OpenCV常见的API及绘图知识详解

时间:2024-07-31 16:29:12浏览次数:13  
标签:const Mat OPenCV int OpenCV API 图像 cv

目录

引言

一、Mat类详解

1. Mat类的基本结构

2. Mat类的数据类型

3. Mat类的创建与初始化

4. Mat类的使用技巧

二、OpenCV核心功能模块

1. 基本的图像读取与显示

2. 图像的保存

3. 矩阵操作

4. 等待键盘输入与销毁窗口

5. 命名窗口

三、图像处理模块

1. 色彩空间转换

2. 图像写入

3. 图像变换

4. 图像滤波

四、绘图与交互

1. 绘制基本图形

  2. 文本绘制

  3. 鼠标与键盘事件

4. 示例:在图像上绘制并响应鼠标事件

五、结论


引言

OpenCV(Open Source Computer Vision Library)是一个开源的计算机视觉和机器学习软件库,它提供了大量的图像处理、视频分析、对象检测等功能。本文将详细介绍OpenCV中常见的API以及绘图相关的知识,帮助开发者更好地理解和使用OpenCV。

一、Mat类详解

Mat类是OpenCV中C++版本的矩阵类,它替代了原来C版本的矩阵结构体CvMat和图像结构体IplImage。Mat类具有许多优势,特别是与STL(Standard Template Library)的兼容性很好,提供了许多类似于STL的操作,并且是一种高效的数据类型,对内存进行动态管理,无需用户手动管理内存。

1. Mat类的基本结构

Mat类定义于OpenCV的core.hpp中,主要包含两部分数据:

  1. 矩阵头(matrix header):这部分的大小是固定的,包含了矩阵的大小(行数和列数)、存储方式、矩阵存储的地址等信息。
  2. 数据指针(data pointer):一个指向矩阵包含像素值的指针,用于访问矩阵的实际数据。

Mat类的定义大致如下(简化版):

class CV_EXPORTS Mat {  
public:  
    int flags; // 包含矩阵的多个标志位,如深度、通道数等  
    int dims;   // 数组的维度,>= 2  
    int rows, cols; // 矩阵的行数和列数  
    uchar* data; // 指向数据的指针  
    int* refcount; // 指向引用计数器的指针  
    // 其他成员...  
};

2. Mat类的数据类型

Mat类支持多种数据类型,这些数据类型决定了矩阵中元素的存储方式。常见的数据类型包括:

  • CV_8U:8位无符号整数(0~255)
  • CV_8S:8位有符号整数(-128~127)
  • CV_16U:16位无符号整数(0~65535)
  • CV_16S:16位有符号整数(-32768~32767)
  • CV_32S:32位有符号整数
  • CV_32F:32位浮点数
  • CV_64F:64位浮点数

在OpenCV中,可以通过特定的模板类(如Mat_<uchar>Mat_<int>等)或类型标识符(如CV_8UC1CV_32FC3等)来指定Mat的数据类型。

3. Mat类的创建与初始化

Mat类可以通过多种方式创建和初始化:

  1. 使用构造函数

    • Mat::Mat():默认构造函数,创建一个空的Mat对象。
    • Mat::Mat(int rows, int cols, int type):指定行数、列数和类型创建Mat对象。
    • Mat::Mat(Size size, int type):使用Size结构体指定尺寸和类型创建Mat对象。
    • Mat::Mat(const Mat& m):拷贝构造函数,创建一个与已有Mat对象相同的Mat对象(但注意,这种方式只是复制了矩阵头,数据是共享的)(浅拷贝)。
  2. 使用create函数:可以在不重新创建Mat对象的情况下改变其大小和类型。

  3. 使用其他函数:如zerosoneseye等,用于创建全零、全一或单位矩阵。

4. Mat类的使用技巧

  1. 元素访问
    • 使用at函数:M.at<type>(i, j),其中type是元素的数据类型,ij是行和列的索引。
    • 使用迭代器:通过MatIterator_迭代器遍历矩阵元素。
    • 使用指针:直接操作data指针访问矩阵数据(注意边界和步长)。
  2. 矩阵操作
    • 支持多种数学运算,如加法、减法、乘法等。
    • 支持矩阵变换,如转置、缩放、旋转等。
  3. 内存管理
    • Mat类自动管理内存,无需用户手动释放。
    • 使用clone函数可以复制整个Mat对象(包括数据),避免数据共享问题。(深拷贝)

二、OpenCV核心功能模块

1. 基本的图像读取与显示

  • cv::imread:用于读取图像文件。其原型为cv::Mat cv::imread(const String& filename, int flags = IMREAD_COLOR)。其中,filename是图像文件的路径,flags是读取图像的方式,例如IMREAD_COLOR表示以彩色模式读取图像,IMREAD_GRAYSCALE表示以灰度模式读取图像。

  • cv::imshow:用于在窗口中显示图像。其原型为void cv::imshow(const String& winname, InputArray mat)。其中,winname是窗口的名称,mat是要显示的图像数据。

2. 图像的保存

  • cv::imwrite:用于将图像写入文件。其原型为bool cv::imwrite(const String& filename, InputArray img, const std::vector<int>& params = std::vector<int>())。其中,filename是保存图像的路径,img是要保存的图像数据,params是保存图像时的一些可选参数。

3. 矩阵操作

  • cv::Mat:是OpenCV中用于存储图像数据和其他多维数组的数据结构。提供了丰富的矩阵操作函数,如加法、减法、乘法、除法、归一化等。

4. 等待键盘输入与销毁窗口

  • cv::waitKey:等待键盘输入。函数原型为int cv::waitKey(int delay = 0)delay参数表示等待时间(毫秒),如果设置为0,则表示无限等待。常用于在显示图像时等待用户按键。
  • cv::destroyAllWindows:销毁所有由OpenCV创建的窗口。

5. 命名窗口

  • cv::namedWindow:用于创建窗口并指定窗口类型。函数原型为void cv::namedWindow(const String& winname, int flags = WINDOW_AUTOSIZE)winname是窗口名称,flags用于指定窗口类型,如WINDOW_AUTOSIZE表示窗口大小自动调整。

三、图像处理模块

1. 色彩空间转换

  • cv::cvtColor:用于图像的色彩空间转换。其原型为void cv::cvtColor(InputArray src, OutputArray dst, int code, int dstCn = 0)。其中,src是输入图像,dst是输出图像,code是转换代码,如COLOR_BGR2GRAY表示将BGR图像转换为灰度图像。

2. 图像写入

  • cv::imwrite:用于将图像写入文件。函数原型为bool cv::imwrite(const String& filename, InputArray img, const std::vector<int>& params = std::vector<int>())filename是输出文件的路径,img是要写入的图像数据。

3. 图像变换

  • cv::resize:用于改变图像的大小。支持多种插值方法,如线性插值、立方插值等。

  • cv::warpAffinecv::warpPerspective:分别用于图像的仿射变换和透视变换。

4. 图像滤波

  • cv::blurcv::GaussianBlur:分别用于图像的均值模糊和高斯模糊。

四、绘图与交互

1. 绘制基本图形

  • cv::line:用于绘制直线。其原型为void cv::line(InputOutputArray img, Point pt1, Point pt2, const Scalar& color, int thickness = 1, int lineType = LINE_8, int shift = 0)。其中,img是绘制图形的载体,pt1pt2是线段的起点和终点,color是线条的颜色,thickness是线条的粗细。

  • cv::rectangle:用于绘制矩形。其原型为void cv::rectangle(InputOutputArray img, Point pt1, Point pt2, const Scalar& color, int thickness = 1, int lineType = LINE_8, int shift = 0)。其中,pt1pt2分别是矩形的左上顶点和右下顶点。

  • cv::circle:用于绘制圆形。其原型为void cv::circle(InputOutputArray img, Point center, int radius, const Scalar& color, int thickness = 1, int lineType = LINE_8, int shift = 0)。其中,center是圆心的坐标,radius是圆的半径。

  • cv::ellipse:用于绘制椭圆。其原型为void cv::ellipse(InputOutputArray img, Point center, Size axes, double angle, double startAngle, double endAngle, const Scalar& color, int thickness = 1, int lineType = LINE_8, int shift = 0)。其中,center是椭圆的圆心坐标,axes是椭圆的长轴和短轴的长度,angle是椭圆的旋转角度。

  • cv::polylines:用于绘制多边形。其原型为void cv::polylines(InputOutputArray img, InputArrayOfArrays pts, bool isClosed, const Scalar& color, int thickness = 1, int lineType = LINE_8, int shift = 0)。其中,pts是多边形的顶点坐标,isClosed表示多边形是否闭合。

  2. 文本绘制

  • cv::putText:用于在图像上绘制文本。其原型为void cv::putText(InputOutputArray img, const String& text, Point org, int fontFace, double fontScale, const Scalar& color, int thickness = 1, int lineType = LINE_8, bool bottomLeftOrigin = false)。其中,img是绘制文本的图像,text是要绘制的文本字符串,org是文本左下角的坐标(如果bottomLeftOriginfalse,则为左下角的坐标,否则为基线的起点),fontFace是字体的类型,fontScale是字体大小的缩放比例,color是文本的颜色,thickness是文本的线条粗细。

  3. 鼠标与键盘事件

OpenCV提供了创建窗口并响应鼠标和键盘事件的功能,这在交互式应用中非常有用。你可以使用cv::namedWindow来创建一个窗口,然后使用cv::setMouseCallbackcv::setKeyboardCallback来分别设置鼠标和键盘的回调函数。

  • cv::namedWindow:创建一个窗口。
  • cv::setMouseCallback:为指定的窗口设置鼠标回调函数。
  • cv::setKeyboardCallback:为指定的窗口设置键盘回调函数。

4. 示例:在图像上绘制并响应鼠标事件

#include <opencv2/opencv.hpp>  
  
void onm ouse(int event, int x, int y, int flags, void* param) {  
    cv::Mat* image = (cv::Mat*)param;  
    if (event == cv::EVENT_LBUTTONDOWN) {  
        cv::circle(*image, cv::Point(x, y), 5, cv::Scalar(0, 255, 0), -1);  
    }  
}  
  
int main() {  
    cv::Mat image = cv::imread("path_to_image.jpg");  
    if (image.empty()) {  
        std::cerr << "Could not read the image" << std::endl;  
        return 1;  
    }  
  
    cv::namedWindow("Image Window", cv::WINDOW_AUTOSIZE);  
    cv::setMouseCallback("Image Window", onm ouse, &image);  
  
    while (true) {  
        cv::imshow("Image Window", image);  
        if (cv::waitKey(20) >= 0) break;  
    }  
  
    return 0;  
}

在这个示例中,我们创建了一个窗口并在其中显示一张图像。通过cv::setMouseCallback设置了一个鼠标回调函数onMouse,该函数会在鼠标左键点击时在图像上绘制一个绿色的圆点。

五、结论

OpenCV提供了丰富的API用于图像处理、图像分析以及绘图等任务。通过本文的介绍,你应该对OpenCV中常见的API以及绘图相关的知识有了更深入的了解。希望这些信息能够帮助你在实际的项目中更加高效地利用OpenCV。

标签:const,Mat,OPenCV,int,OpenCV,API,图像,cv
From: https://blog.csdn.net/weixin_62621696/article/details/140824866

相关文章

  • 0CTF/TCTF 2023 OLAPInfra Nashorn RCE + HDFS UDF RCE
    前置知识ClickHouse:是一个开源的列式数据库管理系统clickhouse-jdbc-bridge:clickhouse数据库和jdbc交互的工具HDFS(HadoopDistributedFileSystem):专为大数据存储和处理而设计。审计<?phperror_reporting(E_ALL^E_DEPRECATED);require__DIR__.'/../vendor/autol......
  • express开发api指南--集成ORM(prisma)
    9.1安装依赖#全局安装prismacnpminstallprisma-g#添加开发依赖cnpminstallprisma--save-dev#创建Prisma架构文件模板,设置PrismaORM项目npxprismainit#安装并生成PrismaClientcnpminstall@prisma/client-gcnpminstall@prisma/client--save9.2连......
  • 使用法兰克福 API 和 Python 虚拟环境时出现 404 错误
    我正在VisualStudioCode中用Python制作货币转换器脚本,并且使用法兰克福API,它在几天前一直工作正常,直到现在每次我尝试获取API时都会收到404错误:|||输出:>response=requests.get(f"https://api.frankfurter.app/latest?amount={amount}&from={CF}&to={CT}")>......
  • 如何使用 Azure Devops API (Python) 提取特定提交的文件内容?
    这就是我想要做的:每次对我的存储库中的特定分支进行提交时,我想提取该提交中更改的所有YAML文件,对其内容进行一些修改,然后将结果作为PR推送到一个新的、独立的分支。我已经弄清楚了这里的大部分步骤,但我陷入了解析提交文件内容部分。我已经尝试过get_item_content和......
  • 由于 OpenAI API 密钥错误,无法使用 Autogen 代理的本地模型
    我正在尝试将Autogen库与本地Huggingface模型一起使用,而不是使用OpenAIAPI。但是,我遇到了一个问题,收到以下错误:OpenAIError:Theapi_keyclientoptionmustbeseteitherbypassingapi_keytotheclientorbysettingtheOPENAI_API_KEYenvironmentvariable......
  • 如何在 FastAPI 中同时接收 JSON 数据和文件上传
    我正在开发一个FastAPI项目,我需要在同一请求中接收JSON数据和文件上传。具体来说,我需要在JSON数据中传递整数数组,同时上传文件。这是我的请求正文的样子:标题(字符串)描述(字符串)评论(字符串)due_date(日期)优先级(字符串)signed_to(数组)整......
  • Flink的DateStream API中的ProcessWindowFunction和AllWindowFunction两种用于窗口处
    目录ProcessWindowFunctionAllWindowFunction具体区别ProcessWindowFunction示例AllWindowFunction示例获取时间不同,一个数据产生的时间一个是数据处理的时间ProcessWindowFunctionAllWindowFunction具体示例ProcessWindowFunction示例AllWindowFunction示例总......
  • 【大模型本地知识库搭建】ChatGLM3,M3E,FastGPT,One-API_fastgpt m3e
    目录引言一、ChatGLM3大模型本地部署二、部署M3E模型三、部署One-API四、部署FastGPT引言本文技术路线为:利用ChatGLM3-6b作为基座大模型,M3E作为向量模型,基于FastGPT建立用户知识库,One-API做统一API接口管理。其中ChatGLM3和M3E模型都是在windows下部署的,FastGPT......
  • go-zero中api从入门到大师
    api文件的学习在go-zero中,api文件可以说是整个项目最重要的一个文件,学好它,写好他,项目相当于已经完成了一半!接下来,我会详细说明.api是什么,以及怎么写先给个案例:typeLoginRequest{ UserNamestring`json:"userName"` Passwordstring`json:"password"`}typeUser......
  • anki Windows 按下z键,使用有道api发音选中英文文本
     <scripttype="text/javascript"> //播放句子的函数 functionplaySentence(sentence){ //构造有道词典的在线朗读URL varyoudaoUrl="https://dict.youdao.com/dictvoice?audio="+encodeURIComponent(sentence); //创建音频元素并播放 varaudio=newAu......