基于opencv3.2和SVM的车牌定位

程序对蓝色车辆检测效果不是很好,有待改进。文字识别和提取正在做
#include"opencv2/opencv.hpp"
#include"opencv2/highgui/highgui.hpp"
#include"opencv2/imgproc/imgproc.hpp"
#include "opencv2/ml.hpp"
#include"iostream"
#include"stdio.h"
using namespace cv;
using namespace std;
bool verify(Rect rect);
int OtsuAlgThreshold(const Mat image);
//void svm_train(SVM & svmClassifier);
int main(int argc, char**argv)
{
 Mat srcimage = imread("7.jpg");
 if (srcimage.data == NULL)
 {
  return 0; cout << "无法加载图片" << endl;
 }


 Mat midimage1, grayimage;
 cvtColor(srcimage, grayimage, CV_BGR2GRAY);
 blur(grayimage, grayimage, Size(3, 3));
 Sobel(grayimage, midimage1, CV_8UC1, 1, 0, 3, 1, 1);
 convertScaleAbs(midimage1, midimage1);
 imshow("1", midimage1);
 ///hsv提取蓝色通道
 Mat midimage2, midimage3;
 cvtColor(srcimage, midimage2, CV_BGR2HSV);
 vector hsv_vec;
 split(midimage2, hsv_vec);
 midimage3 = (hsv_vec[0] > 90)&(hsv_vec[0] < 124)&(hsv_vec[1] > 70)&(hsv_vec[2] > 70);
 imshow("2", midimage3);
 //////形态学处理和找轮廓
 Mat midimage5 = Mat::zeros(srcimage.size(), CV_8UC1);
 midimage5 = midimage3&midimage1;
 imshow("3", midimage5);
 Mat morph;
 morphologyEx(midimage5, morph, MORPH_CLOSE, Mat::ones(2, 25, CV_8UC1));
 vector> contours;
 findContours(morph, contours ,RETR_LIST, CHAIN_APPROX_SIMPLE);
 Rect rec_adapt[30]; int j = 0;
 Mat sizeimage[30], grayResult[30];
 Mat resultResized[30];
 Mat outimage[10];
 //调用SVM文件
 FileStorage fs;
 fs.open("SVM.xml", FileStorage::READ);
 if (!fs.isOpened()) // failed
 {
  std::cout << "Save File Failed!" << std::endl;
  return 0;
 }
 Mat SVM_TrainningData;
 Mat SVM_Classes;
 fs["TrainingData"] >> SVM_TrainningData;
 fs["classes"] >> SVM_Classes;
 //cout << SVM_Classes << endl;
 SVM_Classes.convertTo(SVM_Classes, CV_32SC1);
 cv::Ptr svm = cv::ml::SVM::create();
 svm->setType(cv::ml::SVM::Types::C_SVC);
 svm->setKernel(cv::ml::SVM::KernelTypes::LINEAR);
 svm->setTermCriteria(cv::TermCriteria(cv::TermCriteria::MAX_ITER, 100, 1e-6));
 svm->train(SVM_TrainningData, ml::ROW_SAMPLE, SVM_Classes);
 for (size_t i = 0; i < contours.size(); i++)
 { //绘出所有找到的轮廓
  drawContours(morph, contours, static_cast(i), Scalar(255, 0, 0), 2);
  imshow("4", morph);
  //double car_image_rate = static_cast(countNonZero(morph(boundingRect(contours[i]))) / static_cast(boundingRect(contours[i]).area()));
  //cout << car_image_rate << endl;
  //判定符合车牌条件
  if (verify(boundingRect(contours[i])) == 1)//&& car_image_rate>0.4)
  {  //裁剪图像和直方图均衡化
   rec_adapt[j] = boundingRect(contours[i]);
   sizeimage[j] = srcimage(rec_adapt[j]);
   resize(sizeimage[j], resultResized[j], Size(144, 33), 0, 0, INTER_CUBIC);
   cvtColor(resultResized[j], grayResult[j], CV_BGR2GRAY);
   equalizeHist(grayResult[j], grayResult[j]);
   //grayResult[j].convertTo(grayResult[j], CV_32FC1); 
   //图像矩阵转换成一行
   Mat p = grayResult[j].reshape(1, 1);
   p.convertTo(p, CV_32FC1);
   int response = svm->predict(p);
   if (response == 1)
   {
    outimage[j] = grayResult[j];
    imshow("车牌", outimage[j]);
   }
   else
   {
    cout << "未检索到车牌" << endl;
   }
   j++;
  }
 }
 
  waitKey(0);
 return 0;
 // 
}
bool verify(Rect rect)
{
 float error = 0.4;
 const float aspect = 4.7272;
 int min = 15 * aspect * 15; // 面积下限
 int max = 180 * aspect * 180; // 面积上限
 float rmin = aspect - aspect * error; // 宽高比下限
 float rmax = aspect + aspect * error; // 宽高比上限
 int area = rect.width * rect.height; // 计算面积
 float r = rect.width / rect.height;  // 计算宽高比
 r = r < 1 ? 1 / r : r;
 //return area >= min && area <= max && r >= rmin && r <= rmax&&rect.width>80&& rect.height>10;
 return rect.width > 50 && rect.height > 10 && area >= min && area <= max;
}
以下贴出一张运行图 基于opencv3.2和SVM的车牌定位_第1张图片
工程路径如下 点击打开链接

你可能感兴趣的:(基于opencv3.2和SVM的车牌定位)