采用鼠标事件,手动选择样本点,包括目标样本和背景样本。组成训练数据进行训练

1、主函数

#include "stdafx.h"
#include "opencv2/opencv.hpp"
using namespace cv;
using namespace cv::ml; Mat img,image;
Mat targetData, backData;
bool flag = true;
string wdname = "image"; void on_mouse(int event, int x, int y, int flags, void* ustc); //鼠标取样本点
void getTrainData(Mat &train_data, Mat &train_label); //生成训练数据
void svm(); //svm分类 int main(int argc, char** argv)
{
string path = "d:/peppers.png";
img = imread(path);
img.copyTo(image);
if (img.empty())
{
cout << "Image load error";
return ;
}
namedWindow(wdname);
setMouseCallback(wdname, on_mouse, ); for (;;)
{
imshow("image", img); int c = waitKey();
if ((c & ) == )
{
cout << "Exiting ...\n";
break;
}
if ((char)c == 'c')
{
flag = false;
}
if ((char)c == 'q')
{
destroyAllWindows();
break;
}
}
svm();
return ;
}

首先输入图像,调用setMouseCallback函数进行鼠标取点

2、鼠标事件

//鼠标在图像上取样本点,按q键退出
void on_mouse(int event, int x, int y, int flags, void* ustc)
{
if (event == CV_EVENT_LBUTTONDOWN)
{
Point pt = Point(x, y);
Vec3b point = img.at<Vec3b>(y, x); //取出该坐标处的像素值,注意x,y的顺序
Mat tmp = (Mat_<float>(, ) << point[], point[], point[]);
if (flag)
{
targetData.push_back(tmp); //加入正样本矩阵
circle(img, pt, , Scalar(, , ), -, ); //画圆,在图上显示点击的点 } else
{
backData.push_back(tmp); //加入负样本矩阵
circle(img, pt, , Scalar(, , ), -, ); }
imshow(wdname, img);
}
}

用鼠标在图像上点击,取出当前点的红绿蓝像素值进行训练。先选择任意个目标样本,然后按"c“键后选择任意个背景样本。样本数可以自己随意决定。样本选择完后,按”q"键完成样本选择。

3、svm分类

void getTrainData(Mat &train_data, Mat &train_label)
{
int m = targetData.rows;
int n = backData.rows;
cout << "正样本数::" << m << endl;
cout << "负样本数:" << n << endl;
vconcat(targetData, backData, train_data); //合并所有的样本点,作为训练数据
train_label = Mat(m + n, , CV_32S, Scalar::all()); //初始化标注
for (int i = m; i < m + n; i++)
train_label.at<int>(i, ) = -;
} void svm()
{
Mat train_data, train_label;
getTrainData(train_data, train_label); //获取鼠标选择的样本训练数据 // 设置参数
Ptr<SVM> svm = SVM::create();
svm->setType(SVM::C_SVC);
svm->setKernel(SVM::LINEAR); // 训练分类器
Ptr<TrainData> tData = TrainData::create(train_data, ROW_SAMPLE, train_label);
svm->train(tData); Vec3b color(, , );
// Show the decision regions given by the SVM
for (int i = ; i < image.rows; ++i)
for (int j = ; j < image.cols; ++j)
{
Vec3b point = img.at<Vec3b>(i, j); //取出该坐标处的像素值
Mat sampleMat = (Mat_<float>(, ) << point[], point[], point[]);
float response = svm->predict(sampleMat); //进行预测,返回1或-1,返回类型为float
if ((int)response != )
image.at<Vec3b>(i, j) = color; //将背景点设为黑色
} imshow("SVM Simple Example", image); // show it to the user
waitKey();
}

将正负样本矩阵,用vconcat合并成一个矩阵,用作训练分类器,并对相应的样本进行标注。最后将识别出的目标保留,将背景部分调成黑色。

4、完整程序

// svm.cpp : 定义控制台应用程序的入口点。
// #include "stdafx.h"
#include "opencv2/opencv.hpp"
using namespace cv;
using namespace cv::ml; Mat img,image;
Mat targetData, backData;
bool flag = true;
string wdname = "image"; void on_mouse(int event, int x, int y, int flags, void* ustc); //鼠标取样本点
void getTrainData(Mat &train_data, Mat &train_label); //生成训练数据
void svm(); //svm分类 int main(int argc, char** argv)
{
string path = "d:/peppers.png";
img = imread(path);
img.copyTo(image);
if (img.empty())
{
cout << "Image load error";
return ;
}
namedWindow(wdname);
setMouseCallback(wdname, on_mouse, ); for (;;)
{
imshow("image", img); int c = waitKey();
if ((c & ) == )
{
cout << "Exiting ...\n";
break;
}
if ((char)c == 'c')
{
flag = false;
}
if ((char)c == 'q')
{
destroyAllWindows();
break;
}
}
svm();
return ;
} //鼠标在图像上取样本点,按q键退出
void on_mouse(int event, int x, int y, int flags, void* ustc)
{
if (event == CV_EVENT_LBUTTONDOWN)
{
Point pt = Point(x, y);
Vec3b point = img.at<Vec3b>(y, x); //取出该坐标处的像素值,注意x,y的顺序
Mat tmp = (Mat_<float>(, ) << point[], point[], point[]);
if (flag)
{
targetData.push_back(tmp); //加入正样本矩阵
circle(img, pt, , Scalar(, , ), -, ); //画出点击的点 } else
{
backData.push_back(tmp); //加入负样本矩阵
circle(img, pt, , Scalar(, , ), -, ); }
imshow(wdname, img);
}
} void getTrainData(Mat &train_data, Mat &train_label)
{
int m = targetData.rows;
int n = backData.rows;
cout << "正样本数::" << m << endl;
cout << "负样本数:" << n << endl;
vconcat(targetData, backData, train_data); //合并所有的样本点,作为训练数据
train_label = Mat(m + n, , CV_32S, Scalar::all()); //初始化标注
for (int i = m; i < m + n; i++)
train_label.at<int>(i, ) = -;
} void svm()
{
Mat train_data, train_label;
getTrainData(train_data, train_label); //获取鼠标选择的样本训练数据 // 设置参数
Ptr<SVM> svm = SVM::create();
svm->setType(SVM::C_SVC);
svm->setKernel(SVM::LINEAR); // 训练分类器
Ptr<TrainData> tData = TrainData::create(train_data, ROW_SAMPLE, train_label);
svm->train(tData); Vec3b color(, , );
// Show the decision regions given by the SVM
for (int i = ; i < image.rows; ++i)
for (int j = ; j < image.cols; ++j)
{
Vec3b point = img.at<Vec3b>(i, j); //取出该坐标处的像素值
Mat sampleMat = (Mat_<float>(, ) << point[], point[], point[]);
float response = svm->predict(sampleMat); //进行预测,返回1或-1,返回类型为float
if ((int)response != )
image.at<Vec3b>(i, j) = color; //将背景设置为黑色
} imshow("SVM Simple Example", image);
waitKey();
}

输入原图像:

程序运行后显示:

在opencv3中利用SVM进行图像目标检测和分类的更多相关文章

  1. YOLT:将YOLO用于卫星图像目标检测

    之前作者用滑动窗口和HOG来进行船体监测,在开放水域和港湾取得了不错的成绩,但是对于不一致的复杂背景,这个方法的性能会下降.为了解决这个缺点,作者使用YOLO作为物体检测的流水线,这个方法相比于HOG ...

  2. 使用Caffe完成图像目标检测 和 caffe 全卷积网络

    一.[用Python学习Caffe]2. 使用Caffe完成图像目标检测 标签: pythoncaffe深度学习目标检测ssd 2017-06-22 22:08 207人阅读 评论(0) 收藏 举报 ...

  3. 大尺寸卫星图像目标检测:yoloT

    大尺寸卫星图像目标检测:yoloT 1. 前言 YOLT论文全称「You Only Look Twice: Rapid Multi-Scale Object Detection In Satellit ...

  4. 3D点云点云分割、目标检测、分类

    3D点云点云分割.目标检测.分类 原标题Deep Learning for 3D Point Clouds: A Survey 作者Yulan Guo, Hanyun Wang, Qingyong H ...

  5. tensorflow利用预训练模型进行目标检测(三):将检测结果存入mysql数据库

    mysql版本:5.7 : 数据库:rdshare:表captain_america3_sd用来记录某帧是否被检测.表captain_america3_d用来记录检测到的数据. python模块,包部 ...

  6. tensorflow利用预训练模型进行目标检测(四):检测中的精度问题以及evaluation

    一.tensorflow提供的evaluation Inference and evaluation on the Open Images dataset:https://github.com/ten ...

  7. tensorflow利用预训练模型进行目标检测(一):安装tensorflow detection api

    一.tensorflow安装 首先系统中已经安装了两个版本的tensorflow,一个是通过keras安装的, 一个是按照官网教程https://www.tensorflow.org/install/ ...

  8. tensorflow利用预训练模型进行目标检测(二):预训练模型的使用

    一.运行样例 官网链接:https://github.com/tensorflow/models/blob/master/research/object_detection/object_detect ...

  9. CVPR2020:利用图像投票增强点云中的三维目标检测(ImVoteNet)

    CVPR2020:利用图像投票增强点云中的三维目标检测(ImVoteNet) ImVoteNet: Boosting 3D Object Detection in Point Clouds With ...

随机推荐

  1. Silverlight项目笔记7:xml/json数据解析、TreeView、引用类型与数据绑定错误、图片加载、虚拟目录设置、silverlight安全机制引发的问题、WebClient缓存问题

    1.xml/json数据解析 (1)xml数据解析 使用WebClient获取数据,获取到的数据实例化为一个XDocument,使用XDocument的Descendants(XName)方法获得对应 ...

  2. android 进程/线程管理(三)----Thread,Looper / HandlerThread / IntentService

    Thread,Looper的组合是非常常见的组合方式. Looper可以是和线程绑定的,或者是main looper的一个引用. 下面看看具体app层的使用. 首先定义thread: package ...

  3. 你连Bug都抓不住,还谈什么参与感?

    林子大了什么鸟都有,APP市场也是这样.举个例子,有段时期图片社交井喷式发展,各类图片社交APP一时充斥着市场.各种或重视图片加工或主打社交元素的APP“来得快去得快”.“你方唱罢我登场”,这些短命A ...

  4. maven 错误No goals have been specified for this build. You must specify a valid lifecycle phase or a goal in the format

    [INFO] Scanning for projects... [INFO] ------------------------------------------------------------- ...

  5. c#注册表对象映射

    用于快捷保存与读取注册表,为对应的对象 示例 [RegistryRoot(Name = "superAcxxxxx")] public class Abc : IRegistry ...

  6. Gulp使用入门操作十一步压缩JS

    前提需要安装nodejs 一. 全局安装Gulp npm install -g gulp 二.新建一个 gulpfile.js 文件 chapter2└── gulpfile.js 三.在 gulpf ...

  7. JavaScript生成GUID的算法

    全局唯一标识符(GUID,Globally Unique Identifier)也称作 UUID(Universally Unique IDentifier) . GUID是一种由算法生成的二进制长度 ...

  8. oracle表连接——处理连接过程中另外一张表没有相关数据不显示问题

    一个数据表基本上很难满足我们的查询要求,同时,将所有的数据都保存在一个表格中显然也不是一种好的数据库设计,为了避免数据的冗余,删除.更新异常,我们通常需要建立一张外键表,通过表连接,来获取我们自己想要 ...

  9. ASN.1(抽象语法标记)

    一.简介 ASN.1是一种对分布式计算机系统间交换的数据消息进行抽象描述的规范化语言.   二.教程 http://www.epubit.com.cn/book/onlinechapter/14877

  10. 简单谈谈RAID

    RAID是“Redundant Array of Independent Disk”的缩写,翻译过来叫做独立磁盘的冗余阵列,其实就是磁盘的存储.访问.备份技术.在谈RAID之前,先简单学习一下存储器的 ...