首页 > 其他分享 >OpenCV调用TensorFlow预训练模型

OpenCV调用TensorFlow预训练模型

时间:2023-01-01 11:32:39浏览次数:59  
标签:调用 opencv frame OpenCV TensorFlow coco ssd 2017 size


OpenCV调用TensorFlow预训练模型

      强大OpenCV从自OpenCV 3.1版以来,dnn模块一直是opencv_contrib库的一部分,在3.3版中,它被提到了主仓库中。新版OpenCV dnn模块目前支持Caffe、TensorFlow、Torch、PyTorch等深度学习框架。另外,新版本中使用预训练深度学习模型的API同时兼容C++和Python

其他模型报出各种各样的错误,反正我暂时还没有解决问题,各位神一样的网友若有新的进展,麻烦告知一声,哈哈~!

一、版本配置要求

  • 1. Windows 7 和 VS2015
  • 2. OpenCV3.3.1以上,本人使用的OpenCV 3.4.1,下载地址:​https://github.com/opencv/opencv/releases ​
  • 3.至于TensoFlow,鄙人只是想测试已经训练好的模型,那就可以不安装TensoFlow了,偷懒一下~!

二、模型下载和配置

1.   先用VS2015新建一个项目“opercv4tensorflow”,并在源文件目录下新建 一个“models”的文件夹,这个文件夹用于下载TensoFlow的模型。

2.   目前,只测试TensoFlow的object_detection模块的“ssd_mobilenet_v1_coco_11_06_2017”和“ssd_inception_v2_coco_2017_11_17”两个预训练模型,其他的自己看着办吧:

 

​    http://download.tensorflow.org/models/object_detection/ssd_mobilenet_v1_coco_11_06_2017.tar.gz​

​    http://download.tensorflow.org/models/object_detection/ssd_inception_v2_coco_2017_11_17.tar.gz​

    当然了,你可以自己训练模型,也可以下载更多的预训练模型,这个可以到TensoFlow下载,下载地址是:
​​​     https://github.com/tensorflow/models/blob/master/research/object_detection/g3doc/detection_model_zoo.md​OpenCV调用TensorFlow预训练模型_OpenCV dnn

    Tensorflow模型的graph结构可以保存为.pb文件或者.pbtxt文件,或者.meta文件,其中只有.pbtxt文件是可读的。在OpenCV中,每个模型.pb文件,原则上应有一个对应的文本图形定义的.pbtxt文件,当然也可能没有,在opencv_extra\testdata\dnn有些.pbtxt文件是可以对应找到,这个要看opencv会不会提供,当然,你厉害的话,可以自己按照网络定义结构写一份。

更多的模型,还请网友下方留言,支援一下,我会及时更新博客内容:

序号

.pb文件:预训练模型

.pbtxt文件

备注

1

​ssd_mobilenet_v1_coco_11_06_2017​

ssd_mobilenet_v1_coco.pbtxt

 

2

​ssd_inception_v2_coco_2017_11_17​

ssd_inception_v2_coco_2017_11_17.pbtxt

 

3

 

 

 

4

 

 

 

 

 

 

 

3. 上面下载的TensoFlow模型解压后,里含有重要的二进制protobuf描述的.pb文件,我们还需要对应的protobuf格式文本图形定义的.pbtxt文件,这个就需要到opencv_extra\testdata\dnn下载了

   opencv_extra下载地址:https://github.com/opencv/opencv_extra/tree/master/testdata/dnn

   把dnn文件夹中的“ssd_inception_v2_coco_2017_11_17.pbtxt”和“ssd_mobilenet_v1_coco.pbtxt”也下载复制到项目的models中吧

OpenCV调用TensorFlow预训练模型_OpenCV dnn_02

三、使用opencv读取网络模型

    一切准备妥当了,下面就使用opencv C++(也可以是python的)实现读取TensoFlow训练好的网络模型。opencv dnn为我们提供TensoFlow的接口:readNetFromTensorflow,当然也有支持Caffe的接口:readNetFromCaffe。我们这里只考虑TensoFlow的模型,readNetFromTensorflow函数有多个重载函数:

/** @brief Reads a network model stored in <a href="https://www.tensorflow.org/">TensorFlow</a> framework's format.
* @param model path to the .pb file with binary protobuf description of the network architecture
* @param config path to the .pbtxt file that contains text graph definition in protobuf format.
* Resulting Net object is built by text graph using weights from a binary one that
* let us make it more flexible.
* @returns Net object.
*/
CV_EXPORTS_W Net readNetFromTensorflow(const String &model, const String &config = String());

    完整的测试代码:

#include<opencv2\opencv.hpp>
#include<opencv2\dnn.hpp>
#include <iostream>

using namespace std;
using namespace cv;

const size_t inWidth = 300;
const size_t inHeight = 300;
const float WHRatio = inWidth / (float)inHeight;
const char* classNames[] = { "background","face" };//这个需要根据训练的类别定义

int main() {

Mat frame = cv::imread("2.jpg");
Size frame_size = frame.size();


String weights = "models\\ssd_inception_v2_coco_2017_11_17\\frozen_inference_graph.pb";
String prototxt = "models\\ssd_inception_v2_coco_2017_11_17.pbtxt";
dnn::Net net = cv::dnn::readNetFromTensorflow(weights, prototxt);

Size cropSize;
if (frame_size.width / (float)frame_size.height > WHRatio)
{
cropSize = Size(static_cast<int>(frame_size.height * WHRatio),
frame_size.height);
}
else
{
cropSize = Size(frame_size.width,
static_cast<int>(frame_size.width / WHRatio));
}

Rect crop(Point((frame_size.width - cropSize.width) / 2,
(frame_size.height - cropSize.height) / 2),
cropSize);


cv::Mat blob = cv::dnn::blobFromImage(frame, 1. / 255, Size(300, 300));
//cout << "blob size: " << blob.size << endl;

net.setInput(blob);
Mat output = net.forward();
//cout << "output size: " << output.size << endl;

Mat detectionMat(output.size[2], output.size[3], CV_32F, output.ptr<float>());

frame = frame(crop);
float confidenceThreshold = 0.20;
for (int i = 0; i < detectionMat.rows; i++)
{
float confidence = detectionMat.at<float>(i, 2);

if (confidence > confidenceThreshold)
{
size_t objectClass = (size_t)(detectionMat.at<float>(i, 1));

int xLeftBottom = static_cast<int>(detectionMat.at<float>(i, 3) * frame.cols);
int yLeftBottom = static_cast<int>(detectionMat.at<float>(i, 4) * frame.rows);
int xRightTop = static_cast<int>(detectionMat.at<float>(i, 5) * frame.cols);
int yRightTop = static_cast<int>(detectionMat.at<float>(i, 6) * frame.rows);

ostringstream ss;
ss << confidence;
String conf(ss.str());

Rect object((int)xLeftBottom, (int)yLeftBottom,
(int)(xRightTop - xLeftBottom),
(int)(yRightTop - yLeftBottom));

rectangle(frame, object, Scalar(0, 255, 0), 2);
String label = String(classNames[objectClass]) + ": " + conf;
int baseLine = 0;
Size labelSize = getTextSize(label, FONT_HERSHEY_SIMPLEX, 0.5, 1, &baseLine);
rectangle(frame, Rect(Point(xLeftBottom, yLeftBottom - labelSize.height),
Size(labelSize.width, labelSize.height + baseLine)),
Scalar(0, 255, 0), CV_FILLED);
putText(frame, label, Point(xLeftBottom, yLeftBottom),
FONT_HERSHEY_SIMPLEX, 0.5, Scalar(0, 0, 0));
}
}
imshow("image", frame);
waitKey(0);
return 0;
}

运行结果:

OpenCV调用TensorFlow预训练模型_OpenCV调用TesorFlow模型_03

四、常见的错误和坑

 

  • OpenCV(3.4.1) Error: Unspecified error (FAILED: fs.is_open(). Can't open "models\ssd_inception_v2_coco_2017_1117\frozen_inference_graph.pb")

      出现这个问题,很大的原因是你的模型路径,错鸟!!导致不能打开

  • OpenCV(3.4.1) Error: Unspecified error (Const input blob for weights not found) in cv::dnn::experimental_dnn_v4::`anonymous-namespace'::TFImporter::getConstBlob, file C:\build\master_winpack-build-win64-vc14\opencv\modules\dnn\src\tensorflow\tf_importer.cpp, line 579

     出现这个问题,可能是你的.pb模型文件与.pbtxt文件不对应


标签:调用,opencv,frame,OpenCV,TensorFlow,coco,ssd,2017,size
From: https://blog.51cto.com/u_15764210/5982860

相关文章

  • 将tensorflow训练好的模型移植到Android (MNIST手写数字识别)
    将tensorflow训练好的模型移植到Android(MNIST手写数字识别)​项目​​Github​​下载地址:​​https://github.com/PanJinquan/Mnist-tensorFlow-AndroidDemo​​,麻烦给个......
  • 使用自己的数据集训练GoogLenet InceptionNet V1 V2 V3模型(TensorFlow)
    使用自己的数据集训练GoogLenetInceptionNetV1V2V3模型(TensorFlow)新增博客《​​使用自己的数据集训练MobileNet、ResNet图像识别(TensorFlow)​​》一、前言1、网上已有......
  • OpenCV android sdk配置OpenCV android NDK开发实例
    OpenCVandroidsdk配置OpenCVandroidNDK开发实例    在Android应用中调用OpenCV进行图像处理的方法有很多种,考虑到性能问题,本人推荐使用NDK进行开发,毕竟C/C++要......
  • 如何用python“优雅的”调用有道翻译
    文章目录​​前言​​​​分析​​​​分析url​​​​分析参数01​​​​分析参数02​​​​加密分析​​​​模拟请求​​​​注意点​​​​请求代码​​​​执行结果​......
  • 基于OpenCV的图像梯度与边缘检测!
     Datawhale干货 作者:姚童,Datawhale优秀学习者,华北电力大学严格的说,梯度计算需要求导数。但是图像梯度的计算,是通过计算像素值的差得到梯度的近似值。图像梯度表示的是图像......
  • 基于OpenCV的图像分割处理!
     Datawhale干货 作者:姚童,Datawhale优秀学习者,华北电力大学图像阈值化分割是一种传统的最常用的图像分割方法,因其实现简单、计算量小、性能较稳定而成为图像分割中最基本和......
  • Python__19--函数调用的参数传递与变量的作用域
    1函数调用的参数传递形参(形式参数):在函数定义的时候用到的参数没有具体值,只是一个占位的符号,成为形参;实参(实际参数):在调用函数的时候输入的值。实际参数和形式参......
  • PX01如何实现烧录函数调用--不进行Flicker调整,如烧全代码、烧固定vcom等
    在实际应用中我们经常会碰到烧某些寄存器值为固定值,此时我们并不想进行Flicker调整,按烧录键直接运行烧录函数并实现预期烧录动作,可以的,请参考如下说明。首先,勾选“烧录使......
  • 【win编程】- 在C/C++中调用obj文件
    问题思考:有没有一种方式,让别人用你源码实现的功能,只给你声明,不给你源码?程序编译过程:预编译-编译-链接,编译生成obj文件,最后链接生成可执行文件。那么就可以把源码......
  • 嵌入式:ARM内嵌汇编及C和ARM汇编相互调用
    内嵌汇编在C程序中嵌入汇编程序可以实现一些高级语言没有的功能,并可以提高执行效率。armcc和armcpp内嵌汇编器支持完整的ARM指令集;tcc和tcpp用于Thumb指集。但是内嵌汇编器......