[OpenCV实战]13 OpenCV中使用Mask R

您所在的位置:网站首页 maskrcnn实现实例分割 [OpenCV实战]13 OpenCV中使用Mask R

[OpenCV实战]13 OpenCV中使用Mask R

2023-10-02 06:48| 来源: 网络整理| 查看: 265

目录

1 背景介绍

1.1 什么是图像分割和实例分割

1.2 Mask-RCNN原理

2 Mask-RCNN在OpenCV中的使用

2.1 模型下载

2.2 模型初始化

2.3 模型加载

2.4 输出结果处理

2.5 画图

3 结果和代码

3.1 结果

3.2 代码

4 参考

Mask R-CNN具体内容见:

https://arxiv.org/pdf/1703.06870.pdf

Mask R-CNN最初于2017年11月由Facebook的AI研究团队使用Python和Caffe2推出。工程代码见:

https://github.com/facebookresearch/Detectron

后来Mask R-CNN被移植到Tensorflow,并且在共享了几个预先训练的模型,这些模型具有不同的训练架构,如InceptionV2,ResNet50,ResNet101和Inception-ResnetV2 。它们还为您提供培训自己模型的工具。

https://github.com/tensorflow/models/blob/master/research/object_detection/g3doc/detection_model_zoo.md

https://github.com/tensorflow/models/blob/master/research/object_detection/g3doc/instance_segmentation.md

基于Inception训练的Mask R-CNN速度最快,甚至可以在CPU上试用它,因此我们在本教程中选择了它。该模型在MSCOCO数据集上进行了训练。我们将共享OpenCV(OpenCV 3.43以上版本)代码以在C ++和Python中加载和使用该模型。

1 背景介绍 1.1 什么是图像分割和实例分割

在计算机视觉中,术语“图像分割”或简称“分割”意味着基于某些标准将图像分成像素区域。您可以根据颜色,纹理或您已决定的其他一些条件进行分割。这些区域有时也称为超像素区域。

进行图像分割有多种方法比如实例分割,语义分割,全景分割等。

具体区别见:

https://zhuanlan.zhihu.com/p/50996404

在实例分割中,目标是检测图像中的特定对象并在感兴趣的对象周围创建掩模。实例分割也可以被认为是对象检测,其输出是掩码而不仅仅是边界框。与尝试对图像中的每个像素进行分类的语义分割不同,实例分割不仅仅在标记图像中的每个像素,还区分各个单体。下面我们看一个在非常相似的彩色背景上的两只绵羊的实例分割的例子。

https://www.learnopencv.com/wp-content/uploads/2018/10/Mask-RCNN-results-1024x290.png

1.2 Mask-RCNN原理

Mask-RCNN是对原始R-CNN论文的一系列改进结果,用于物体检测。R-CNN基于选择性搜索的方法生成候选框,然后使用卷积网络一次一个地处理每个候选框区域以输出对象标签及其边界框。

R-CNN具体见:

https://arxiv.org/abs/1311.2524

Fast R-CNN通过使用ROIPool层在其CNN中一起处理所有提出的候选框区域,使得R-CNN算法更快。

Fast R-CNN具体见:

https://arxiv.org/pdf/1504.08083.pdf

Faster R-CNN通过提取候选区域的网络RPN,代替了费时的选择性搜索,使得检测速度大幅提高。

Faster R-CNN具体见:

https://arxiv.org/pdf/1506.01497.pdf

上述R-CNN及其优化版本简要原理见:

https://www.cnblogs.com/skyfsm/p/6806246.html

Mask R-CNN是对Faster RCNN的一种改进,它包括掩码预测与标签预测和边界框预测两个输出,如下图所示:

Mask-RCNN网络有两个主要部分。

第一个是候选区域生成网络,每个图像生成大约300个候选区域。在训练期间,这些候选区域(ROI)中的每一个都通过第二部分,即目标检测和掩模预测网络,如上所示。注意,由于掩模预测分支与分类框预测分支并行运行,因此对于每个给定的ROI,网络预测可能会获得属于任何类别的掩模。

在推理期间,候选区域会用非最大抑制性方法进行筛选,并且掩模预测分支仅处理最高得分100检测框。因此,对于100个ROI和90个对象类,网络的掩模预测部分输出尺寸为100x90x15x15的4D张量,其中每个掩模的大小为15×15。

对于上面显示的绵羊图像,网络检测到两个对象。对于每个对象,它输出一个数组,其中包含预测的类分数(表示对象属于预测类的概率),检测到的对象的边界框的左,上,右和下位置。从掩码预测分支的输出中提取相应分类的掩码。检测到的两个对象的掩码如下所示:

与Faster R-CNN一样,Mask R-CNN所用架构网络也很灵活。我们之所以选择InceptionV2是因为速度更快,但正如Mask R-CNN论文的作者所指出的那样,人们可以通过ResNeXt-101这样的更好的架构获得更好的结果。

与其他物体探测器(如YOLOv3)相比,Mask-RCNN网络可在更大的图像上运行。网络调整输入图像的大小,使得较小的边是800像素。下面我们将详细介绍获取实例分段结果所需的步骤。为了简化和清晰可视化,我们使用相同的颜色来表示同一类的对象,

Mask R-CNN简要理解见:

https://www.cnblogs.com/wangyong/p/9305347.html

2 Mask-RCNN在OpenCV中的使用 2.1 模型下载

模型下载地址:

http://download.tensorflow.org/models/object_detection/mask_rcnn_inception_v2_coco_2018_01_28.tar.gz

2.2 模型初始化

Mask-RCNN算法输出生成为边界框。每个边界框与置信度分数相关联。置信度阈值参数以下的都将被忽略。从网络输出的对象掩码是灰度图像。由于我们在本教程中使用二值掩码,因此我们使用maskThreshold参数来阈值灰色掩码图像。降低其值将获取更大的掩模。有时这有助于包括在边界附近遗漏的部分,但同时,它还可能包括更尖的边界区域处的背景像素。

文件mscoco_labels.names包含训练模型的所有预测对象。colors.txt文件包含用于标记各种类对象的所有颜色。

接下来,我们使用这两个文件加载网络 

mask_rcnn_inception_v2_coco.pb:预先训练的权重;

mask_rcnn_inception_v2_coco.pbtxt:模型结构文件;

下载后的文件有个frozen_inference_graph.pb文件,我改成了mask_rcnn_inception_v2_coco.pb。

我们在这里将DNN后端设置为OpenCV,将目标设置为CPU。您可以尝试将首选目标设置为cv.dnn.DNN_TARGET_OPENCL以在GPU上运行它。当前OpenCV版本中的DNN模块仅使用英特尔的GPU进行测试。我们将读取图像,视频流或网络摄像头进行检测。

C++代码如下:

//0-image,1-video,2-camera int read_file = 0; // Load names of classes 导入分类名文件 string classesFile = "./model/mscoco_labels.names"; ifstream ifs(classesFile.c_str()); string line; while (getline(ifs, line)) { classes.push_back(line); } // Load the colors 导入颜色类文件 string colorsFile = "./model/colors.txt"; ifstream colorFptr(colorsFile.c_str()); while (getline(colorFptr, line)) { char *pEnd; double r, g, b; //字符串转换成浮点数 r = strtod(line.c_str(), &pEnd); g = strtod(pEnd, NULL); b = strtod(pEnd, NULL); Scalar color = Scalar(r, g, b, 255.0); colors.push_back(Scalar(r, g, b, 255.0)); } // Give the configuration and weight files for the model String textGraph = "./model/mask_rcnn_inception_v2_coco.pbtxt"; String modelWeights = "./model/mask_rcnn_inception_v2_coco.pb"; 2.3 模型加载

神经网络的输入图像需要采用称为blob的特定格式。这一点类似于其他OpenCV调用深度学习网络的架构。但是用于我们调用的是tensorflow的模型,所以swapRGB参数设置为true。Caffe模型就不需要。

然后将blob作为其输入传递到网络,但是我们需要事先设定获取网络的输出层名字。因为输出有两个。这个模型有detection_out_final和detection_masks两个输出层。 这两个输出层分别为预测框的输出结果层和掩模的输出结果层。我们将在下一节中滤除低置信度分数的框。

C++代码如下:

// Load the network 导入网络 Net net = readNetFromTensorflow(modelWeights, textGraph); net.setPreferableBackend(DNN_BACKEND_OPENCV); //只使用CPU net.setPreferableTarget(DNN_TARGET_CPU); // Open a video file or an image file or a camera stream. string str, outputFile; VideoCapture cap; VideoWriter video; Mat frame, blob; try { //输出文件,默认是视频 outputFile = "mask_rcnn_out_cpp.avi"; if (read_file == 0) { // Open the image file 打开图像文件 str = "image/cars.jpg"; //cout


【本文地址】


今日新闻


推荐新闻


CopyRight 2018-2019 办公设备维修网 版权所有 豫ICP备15022753号-3