前言

学习了很长一段时间了,需要沉淀下,而最好的办法就是做一个东西来应用学习的东西,同时也是一个学习的过程。

PS:这篇小文是毕业之前和同学做的一个小项目,所以写的比较匆忙,代码也是直接粘贴的,基于qt开发的C++代码,不能保证没有错误,请慎重。不希望对你产生误导,有任何问题可以联系我,一起探讨下。最后,我现在已经没有搞嵌入式方面的开发了。

概述    

OpenCV的全称是:Open Source Computer Vision Library。OpenCV是一个基于(开源)发行的跨平台计算机视觉库,可以运行在Linux、Windows和Mac OS操作系统上。它轻量级而且高效——由一系列 C 函数和少量 C++ 类构成,同时提供了Python、Ruby、MATLAB等语言的接口,实现了图像处理和计算机视觉方面的很多通用算法。

来自百度的解释,之所以选择opencv是因为:首先向学习一个新的东西来看看自己的学习接受能力,然后是感觉opencv很酷,处理图片真实说一不二的(你可以理解为处理图片很方便)。

车牌识别系统重点在于车牌的识别,还有后台的处理。要使它成为一个系统,缺一不可。

大致上分为三个部分:信息采集和传输,接收图片并识别客户端请求,信息的存储和查询


1.信息采集和传输

这里我们采用的是 网上买的小摄像头+网上的开源项目mjpg-stream

对于mjpg-stream的使用,网上已经有很多博客了,你可以找到很多。

mjpg-stream 不仅能调用摄像头拍摄照片还可以作为服务器发送图片数据,所以我这里直接使用它作为服务器发送给我自己写的客户端数据。

2.接收图片并进行图片识别和显示

这里就需要用到opencv来进行处理了。

大致上车牌识别分为:车牌提取,字符提取,字符识别

车牌提取:需要调用opencv里面图片处理的几个函数接口:

灰度处理-》竖向边缘检测(因为车牌大部分竖向的)-》二值化处理-》形态学处理-》车牌截取

  1. string read_plate(string path)
  2. {
  3. /*加载图片*/
  4. const char* imagename = path.c_str();
  5. IplImage * img = cvLoadImage(imagename);
  6. if(!img)
  7. {
  8. exit();
  9. }
  10.  
  11. if( !img->imageData ) // 检查是否正确载入图像
  12. exit();
  13.  
  14. cvNamedWindow("image", CV_WINDOW_AUTOSIZE); //创建窗口
  15. // cvShowImage("image", img); //显示图像
  16. /*灰度化处理*/
  17. IplImage* img1 = cvCreateImage(cvGetSize(img), IPL_DEPTH_8U, );//创建目标图像
  18. cvCvtColor(img,img1,CV_BGR2GRAY);//cvCvtColor(src,des,CV_BGR2GRAY)
  19. cvNamedWindow("gray_image",CV_WINDOW_AUTOSIZE);//创建显示目标的窗口
  20.  
  21. // cvShowImage("gray_image",img1);//显示灰度图像
  22. /*滤波处理*/
  23. IplImage* temp = cvCreateImage(cvGetSize(img1), IPL_DEPTH_8U, );//创建目标图像
  24. cvSmooth(img1,temp,CV_GAUSSIAN,,);//高斯模糊
  25. // cvShowImage("guolv_image",temp);//显示过滤图
  26.  
  27. /*竖向边缘检测 竖向只是参数的改变*/
  28. IplImage * sobel=cvCreateImage(cvGetSize(temp),IPL_DEPTH_16S,);
  29. IplImage *sobelimg=cvCreateImage(cvGetSize(temp),IPL_DEPTH_8U,);
  30. cvSobel(temp,sobel,,,);
  31. cvConvertScaleAbs(sobel,sobelimg, 0.00390625,);
  32. // cvShowImage("灰度图像Sobel变换",sobelimg);
  33.  
  34. /*二值化处理*/
  35. IplImage *two=cvCreateImage(cvGetSize(temp),IPL_DEPTH_8U,);
  36. cvThreshold(sobelimg, two, , , CV_THRESH_BINARY| CV_THRESH_OTSU);
  37. // cvShowImage("two",two);
  38.  
  39. /*形态学处理 腐蚀膨胀*/
  40. IplImage *closeimg=cvCreateImage(cvGetSize(temp),IPL_DEPTH_8U,);
  41. IplConvKernel* kernal=cvCreateStructuringElementEx(,, , , CV_SHAPE_RECT);
  42. cvDilate(two, closeimg, kernal, );
  43. cvErode(closeimg, closeimg, kernal, );
  44. cvDilate(closeimg, closeimg, kernal, );
  45. kernal = cvCreateStructuringElementEx(, , , , CV_SHAPE_RECT);
  46. cvErode(closeimg, closeimg, kernal, );
  47. cvDilate(closeimg, closeimg, kernal, );
  48. //cvShowImage("closeimg",closeimg);
  49.  
  50. /*筛选最大的那块矩形*/
  51. IplImage* copy = cvCloneImage(closeimg);
  52. IplImage* dst = cvCloneImage(img);
  53. CvMemStorage* storage = cvCreateMemStorage();
  54. CvSeq* contours;
  55. CvRect rect,max;
  56. int count=;
  57. double wide=,height=;
  58. count= cvFindContours (copy, storage, &contours, sizeof(CvContour), CV_RETR_LIST, CV_CHAIN_APPROX_NONE);
  59. for (;contours != NULL; contours = contours->h_next)
  60. {
  61. rect = cvBoundingRect(contours);
  62. if(rect.width > (rect.height*))
  63. {
  64. if(rect.height>height && rect.width>wide)
  65. {
  66. max = rect;
  67. height = rect.height;
  68. wide = rect.width;
  69.  
  70. }
  71. }
  72. }
  73. cvSetImageROI(dst,cvRect(max.x+,max.y+,max.width-,max.height-));
  74. cvShowImage("choose",dst);
  75.  
  76. }

plate shot

代码中对截取车牌进行了操作

下面是字符的识别:字符识别有很多方法,但是都是算法的,我研究的不是很深,选取了最简单的一种,自己做字符库,然后比对。

  1. //车牌识别
  2. #include "char.h"
  3.  
  4. //中文字模 注意绝对路径= =
  5. const char *mb_ku_zw[] = {
  6. "/home/panhao/QtProject/MyANPR/char_img/zw1.bmp","/home/panhao/QtProject/MyANPR/char_img/zw2.bmp","/home/panhao/QtProject/MyANPR/char_img/zw3.bmp",
  7. "/home/panhao/QtProject/MyANPR/char_img/zw4.bmp","/home/panhao/QtProject/MyANPR/char_img/zw5.bmp",
  8. "/home/panhao/QtProject/MyANPR/char_img/zw6.bmp","/home/panhao/QtProject/MyANPR/char_img/zw7.bmp","/home/panhao/QtProject/MyANPR/char_img/zw8.bmp",
  9. "/home/panhao/QtProject/MyANPR/char_img/zw9.bmp","/home/panhao/QtProject/MyANPR/char_img/zw10.bmp","/home/panhao/QtProject/MyANPR/char_img/zw11.bmp",
  10. "/home/panhao/QtProject/MyANPR/char_img/zw12.bmp","/home/panhao/QtProject/MyANPR/char_img/zw13.bmp","/home/panhao/QtProject/MyANPR/char_img/zw14.bmp",
  11. "/home/panhao/QtProject/MyANPR/char_img/zw15.bmp","/home/panhao/QtProject/MyANPR/char_img/zw16.bmp","/home/panhao/QtProject/MyANPR/char_img/zw17.bmp",
  12. "/home/panhao/QtProject/MyANPR/char_img/zw18.bmp","/home/panhao/QtProject/MyANPR/char_img/zw19.bmp","/home/panhao/QtProject/MyANPR/char_img/zw20.bmp",
  13. "/home/panhao/QtProject/MyANPR/char_img/zw21.bmp","/home/panhao/QtProject/MyANPR/char_img/zw22.bmp","/home/panhao/QtProject/MyANPR/char_img/zw23.bmp",
  14. "/home/panhao/QtProject/MyANPR/char_img/zw24.bmp","/home/panhao/QtProject/MyANPR/char_img/zw25.bmp","/home/panhao/QtProject/MyANPR/char_img/zw26.bmp",
  15. "/home/panhao/QtProject/MyANPR/char_img/zw27.bmp","/home/panhao/QtProject/MyANPR/char_img/zw28.bmp","/home/panhao/QtProject/MyANPR/char_img/zw29.bmp",
  16. "/home/panhao/QtProject/MyANPR/char_img/zw30.bmp","/home/panhao/QtProject/MyANPR/char_img/zw31.bmp",
  17. };
  18. const char *mb_ku_zf[] ={
  19. "/home/panhao/QtProject/MyANPR/char_img/A.bmp","/home/panhao/QtProject/MyANPR/char_img/B.bmp",
  20. "/home/panhao/QtProject/MyANPR/char_img/C.bmp","/home/panhao/QtProject/MyANPR/char_img/D.bmp",
  21. "/home/panhao/QtProject/MyANPR/char_img/E.bmp","/home/panhao/QtProject/MyANPR/char_img/F.bmp",
  22. "/home/panhao/QtProject/MyANPR/char_img/G.bmp","/home/panhao/QtProject/MyANPR/char_img/H.bmp",
  23. "/home/panhao/QtProject/MyANPR/char_img/J.bmp","/home/panhao/QtProject/MyANPR/char_img/K.bmp",
  24. "/home/panhao/QtProject/MyANPR/char_img/L.bmp","/home/panhao/QtProject/MyANPR/char_img/M.bmp",
  25. "/home/panhao/QtProject/MyANPR/char_img/N.bmp","/home/panhao/QtProject/MyANPR/char_img/P.bmp",
  26. "/home/panhao/QtProject/MyANPR/char_img/Q.bmp","/home/panhao/QtProject/MyANPR/char_img/R.bmp",
  27. "/home/panhao/QtProject/MyANPR/char_img/S.bmp","/home/panhao/QtProject/MyANPR/char_img/T.bmp",
  28. "/home/panhao/QtProject/MyANPR/char_img/U.bmp","/home/panhao/QtProject/MyANPR/char_img/V.bmp",
  29. "/home/panhao/QtProject/MyANPR/char_img/W.bmp","/home/panhao/QtProject/MyANPR/char_img/X.bmp",
  30. "/home/panhao/QtProject/MyANPR/char_img/Y.bmp","/home/panhao/QtProject/MyANPR/char_img/Z.bmp",
  31. };
  32. const char *mb_ku_sz[] ={
  33. "/home/panhao/QtProject/MyANPR/char_img/0.bmp","/home/panhao/QtProject/MyANPR/char_img/1.bmp","/home/panhao/QtProject/MyANPR/char_img/2.bmp",
  34. "/home/panhao/QtProject/MyANPR/char_img/3.bmp","/home/panhao/QtProject/MyANPR/char_img/4.bmp","/home/panhao/QtProject/MyANPR/char_img/5.bmp",
  35. "/home/panhao/QtProject/MyANPR/char_img/6.bmp","/home/panhao/QtProject/MyANPR/char_img/7.bmp","/home/panhao/QtProject/MyANPR/char_img/8.bmp",
  36. "/home/panhao/QtProject/MyANPR/char_img/9.bmp",
  37. };
  38. const char *mb_ku_sf[] = {
  39. "/home/panhao/QtProject/MyANPR/char_img/0.bmp","/home/panhao/QtProject/MyANPR/char_img/1.bmp","/home/panhao/QtProject/MyANPR/char_img/2.bmp",
  40. "/home/panhao/QtProject/MyANPR/char_img/3.bmp","/home/panhao/QtProject/MyANPR/char_img/4.bmp","/home/panhao/QtProject/MyANPR/char_img/5.bmp",
  41. "/home/panhao/QtProject/MyANPR/char_img/6.bmp","/home/panhao/QtProject/MyANPR/char_img/7.bmp","/home/panhao/QtProject/MyANPR/char_img/8.bmp",
  42. "/home/panhao/QtProject/MyANPR/char_img/9.bmp","/home/panhao/QtProject/MyANPR/char_img/A.bmp","/home/panhao/QtProject/MyANPR/char_img/B.bmp",
  43. "/home/panhao/QtProject/MyANPR/char_img/C.bmp","/home/panhao/QtProject/MyANPR/char_img/D.bmp","/home/panhao/QtProject/MyANPR/char_img/E.bmp",
  44. "/home/panhao/QtProject/MyANPR/char_img/F.bmp","/home/panhao/QtProject/MyANPR/char_img/G.bmp","/home/panhao/QtProject/MyANPR/char_img/H.bmp",
  45. "/home/panhao/QtProject/MyANPR/char_img/J.bmp","/home/panhao/QtProject/MyANPR/char_img/K.bmp","/home/panhao/QtProject/MyANPR/char_img/L.bmp",
  46. "/home/panhao/QtProject/MyANPR/char_img/M.bmp","/home/panhao/QtProject/MyANPR/char_img/N.bmp","/home/panhao/QtProject/MyANPR/char_img/P.bmp",
  47. "/home/panhao/QtProject/MyANPR/char_img/Q.bmp","/home/panhao/QtProject/MyANPR/char_img/R.bmp","/home/panhao/QtProject/MyANPR/char_img/S.bmp",
  48. "/home/panhao/QtProject/MyANPR/char_img/T.bmp","/home/panhao/QtProject/MyANPR/char_img/U.bmp","/home/panhao/QtProject/MyANPR/char_img/V.bmp",
  49. "/home/panhao/QtProject/MyANPR/char_img/W.bmp","/home/panhao/QtProject/MyANPR/char_img/X.bmp","/home/panhao/QtProject/MyANPR/char_img/Y.bmp",
  50. "/home/panhao/QtProject/MyANPR/char_img/Z.bmp",
  51.  
  52. };
  53.  
  54. string shibie(char *imgpath)
  55. {
  56. IplImage *pSrcImage = cvLoadImage(imgpath, ); //定位后车牌路径
  57. IplImage *pGrayImage = NULL;
  58. IplImage *pBinaryImage = NULL;
  59. IplImage *ty_cpimg = NULL;
  60. // 转为灰度图
  61. pGrayImage = cvCreateImage(cvGetSize(pSrcImage), IPL_DEPTH_8U, );
  62. cvCvtColor(pSrcImage, pGrayImage, CV_BGR2GRAY);
  63. // 创建二值图
  64. pBinaryImage = cvCreateImage(cvGetSize(pGrayImage), IPL_DEPTH_8U, );
  65. //转为二值图,自适二值化CV_THRESH_OTSU
  66. cvThreshold(pGrayImage, pBinaryImage, , , CV_THRESH_BINARY | CV_THRESH_OTSU);
  67.  
  68. cvNamedWindow("input",);
  69. cvShowImage("input",pBinaryImage);
  70.  
  71. //识别铆钉
  72. const int height_md_yz = pBinaryImage->height / ; //y轴方向的阈值
  73. const int width_md_yz = pBinaryImage->width; //x轴方向的阈值
  74. IplImage* cyp = cvCloneImage( pBinaryImage );
  75. int width_md = ;
  76. int height_md = ;
  77. int count_bd = ;
  78. uchar count_bd_str[width_md_yz];
  79. for(count_bd = ; count_bd < width_md_yz; count_bd++)
  80. count_bd_str[count_bd] = ;
  81. uchar *pt = (uchar *)cyp->imageData;
  82. const uchar step = cyp->widthStep;
  83.  
  84. //扫描白点并记录
  85. for(width_md = ; width_md < width_md_yz; width_md++)
  86. {
  87. for(height_md = ; height_md < height_md_yz; height_md++)
  88. {
  89. if(pt[height_md*step + width_md])
  90. count_bd_str[width_md]++;
  91. }
  92. }
  93.  
  94. int width_bf = ;
  95. int width_ls = ;
  96. for(width_md = ; width_md < width_md_yz; width_md++)
  97. {
  98. if(count_bd_str[width_md] > height_md_yz/)
  99. if(width_md < width_md_yz-)
  100. if(count_bd_str[++width_md]> height_md_yz/)
  101. {
  102. if(!width_bf)
  103. {
  104. if(width_md > width_md_yz*0.2)
  105. width_bf = width_md;
  106. }
  107. else if(width_md - width_bf > width_md_yz/)
  108. {
  109. if(width_md > width_md_yz*0.6)
  110. width_ls = width_md;
  111. }
  112. }
  113. }
  114. //如果判断是柳钉则使用柳钉计算比例定位
  115. if(width_md_yz*0.4 < (width_ls - width_bf) && (width_ls - width_bf) < width_md_yz*0.6)
  116. {
  117. float img_bl = ((float)(width_ls - width_bf))/;
  118. int width_left_new = width_bf - (int)(img_bl*);
  119. int width_right_new = width_ls + (int)(img_bl*);
  120. if(width_left_new<)width_left_new=;
  121. if(width_right_new>pBinaryImage->width)width_right_new=pBinaryImage->width;
  122. int height_top_new = ;
  123. int height_down_new = pBinaryImage->height;
  124. const uchar height_yz_x = pBinaryImage->height/;
  125. uchar count_bd_x_str[height_yz_x];
  126. for(count_bd = ; count_bd < height_yz_x; count_bd++) //数组清零
  127. count_bd_x_str[count_bd] = ;
  128. for(int height_ydw = ; height_ydw < height_yz_x; height_ydw++)
  129. {
  130. for(width_md = ; width_md < width_md_yz; width_md++)
  131. {
  132. if(pt[height_ydw*step + width_md])
  133. count_bd_x_str[height_ydw]++;
  134. }
  135. }
  136. for(int height_ydw = ; height_ydw < height_yz_x; height_ydw++)
  137. {
  138. if(count_bd_x_str[height_ydw] < (int)(pBinaryImage->width*/)) //切割条件->白点个数 阈值
  139. height_top_new = height_ydw;
  140. }
  141.  
  142. for(count_bd = ; count_bd < height_yz_x; count_bd++)
  143. count_bd_x_str[count_bd] = ;
  144. for(int height_ydw = ; height_ydw < height_yz_x; height_ydw++)
  145. {
  146. for(width_md = ; width_md < width_md_yz; width_md++)
  147. {
  148. if(pt[(pBinaryImage->height - height_ydw)*step + width_md])
  149. count_bd_x_str[height_ydw]++;
  150. }
  151. }
  152. for(int height_ydw = ; height_ydw < height_yz_x; height_ydw++)
  153. {
  154. if(count_bd_x_str[height_ydw] < (int)(pBinaryImage->width*/))
  155. height_down_new = pBinaryImage->height - height_ydw;
  156. }
  157.  
  158. IplImage* cyp_ptx = cvCloneImage( pBinaryImage );
  159. CvRect ptx;
  160. ptx.x = width_left_new;
  161. ptx.y = height_top_new;
  162. ptx.height = height_down_new - height_top_new;
  163. ptx.width = width_right_new - width_left_new;
  164. cvSetImageROI(cyp_ptx, ptx);
  165. cvSaveImage("/home/panhao/QtProject/MyANPR/img/cyp_ptx.jpg", cyp_ptx);
  166. ty_cpimg = cvCloneImage(cyp_ptx);
  167. cvResetImageROI(cyp_ptx);
  168. }
  169. //如果无法识别铆钉,那就先投影切割后按比例切割字符
  170. else
  171. {
  172. int width_left_new_y = ;
  173. int width_right_new_y = pBinaryImage->width;
  174. int height_top_new_y = ;
  175. int height_down_new_y = pBinaryImage->height;
  176. const uchar height_yz_y = pBinaryImage->height/;
  177. const uchar width_yz_y = pBinaryImage->width/; //阈值 请修改
  178. uchar width_bd_ptr_y[width_yz_y];
  179. uchar height_bd_ptr_y[height_yz_y];
  180. for(count_bd = ; count_bd < width_yz_y; count_bd++)
  181. width_bd_ptr_y[count_bd] = ;
  182. for(count_bd = ; count_bd < height_yz_y; count_bd++)
  183. height_bd_ptr_y[count_bd] = ;
  184. for(int width_yd_y = ; width_yd_y < width_yz_y; width_yd_y++)
  185. for(int height_yd_y = ; height_yd_y < pBinaryImage->height; height_yd_y++)
  186. {
  187. if(pt[height_yd_y*step + width_yd_y])
  188. width_bd_ptr_y[width_yd_y]++;
  189. }
  190. for(int width_yd_y = ; width_yd_y < width_yz_y; width_yd_y++)
  191. {
  192. if(width_bd_ptr_y[width_yd_y] < (int)(pBinaryImage->height*/))
  193. width_left_new_y = width_yd_y;
  194. // int x = width_bd_ptr_y[width_yd_y];
  195. }
  196. for(count_bd = ; count_bd < width_yz_y; count_bd++)
  197. width_bd_ptr_y[count_bd] = ;
  198. for(int width_yd_y = ; width_yd_y < width_yz_y; width_yd_y++)
  199. for(int height_yd_y = ; height_yd_y < pBinaryImage->height; height_yd_y++)
  200. {
  201. if(pt[height_yd_y*step + pBinaryImage->width - width_yd_y])
  202. width_bd_ptr_y[width_yd_y]++;
  203. }
  204. for(int width_yd_y = ; width_yd_y < width_yz_y; width_yd_y++)
  205. {
  206. if(width_bd_ptr_y[width_yd_y] < (int)(pBinaryImage->height*/))
  207. width_right_new_y =pBinaryImage->width - width_yd_y;
  208. }
  209.  
  210. for(int height_yd_y = ; height_yd_y < height_yz_y; height_yd_y++)
  211. for(int width_yd_y = ; width_yd_y < pBinaryImage->width; width_yd_y++)
  212. {
  213. if(pt[height_yd_y*step + width_yd_y])
  214. height_bd_ptr_y[height_yd_y]++;
  215. }
  216. for(int height_yd_y = ; height_yd_y < height_yz_y; height_yd_y++)
  217. {
  218. if(height_bd_ptr_y[height_yd_y] < (int)(pBinaryImage->width*/))
  219. height_top_new_y = height_yd_y;
  220. }
  221. for(count_bd = ; count_bd < height_yz_y; count_bd++)
  222. height_bd_ptr_y[count_bd] = ;
  223. for(int height_yd_y = ; height_yd_y < height_yz_y; height_yd_y++)
  224. for(int width_yd_y = ; width_yd_y < pBinaryImage->width; width_yd_y++)
  225. {
  226. if(pt[(pBinaryImage->height - height_yd_y)*step + width_yd_y])
  227. height_bd_ptr_y[height_yd_y]++;
  228. }
  229. for(int height_yd_y = ; height_yd_y < height_yz_y; height_yd_y++)
  230. {
  231. if(height_bd_ptr_y[height_yd_y] < (int)(pBinaryImage->width*/)) //上下切
  232. height_down_new_y = pBinaryImage->height - height_yd_y;
  233. }
  234. IplImage* cyp_ptx = cvCloneImage( pBinaryImage );
  235. CvRect ptx;
  236. ptx.x = width_left_new_y;
  237. ptx.y = height_top_new_y;
  238. ptx.height = height_down_new_y - height_top_new_y;
  239. ptx.width = width_right_new_y - width_left_new_y;
  240. cvSetImageROI(cyp_ptx, ptx);
  241. cvSaveImage("/home/panhao/QtProject/MyANPR/img/cyp_ptx_y.jpg", cyp_ptx); //保存查看投影切割的结果
  242. ty_cpimg = cvCloneImage(cyp_ptx);
  243. cvResetImageROI(cyp_ptx);
  244. }
  245.  
  246. //图片统一尺寸180x40 开始字符切割(字符切割使用的是最最简单的按比例切割,效果不是很理想,如果要高识别率,需要对字符进行上下左右的投影切割,然后再进行归一化,这样可以提高识别率)
  247. IplImage *img_ty = NULL;
  248. CvSize dst_cvsize;
  249. dst_cvsize.height = ;
  250. dst_cvsize.width = ;
  251. img_ty = cvCreateImage(dst_cvsize, ty_cpimg->depth, ty_cpimg->nChannels);
  252. cvResize(ty_cpimg, img_ty, CV_INTER_LINEAR); //二线性插值法会出现灰度
  253. ty_cpimg = cvCloneImage( img_ty );
  254. cvThreshold(ty_cpimg, img_ty, , , CV_THRESH_BINARY | CV_THRESH_OTSU); //再次二值化
  255. cvSaveImage("/home/panhao/QtProject/MyANPR/img/img_ty.jpg", img_ty);
  256. dst_cvsize.height = ;
  257. dst_cvsize.width = ;
  258. IplImage *pic1 = cvCreateImage(dst_cvsize, img_ty->depth, img_ty->nChannels);
  259. IplImage *pic2 = cvCreateImage(dst_cvsize, img_ty->depth, img_ty->nChannels);
  260. IplImage *pic3 = cvCreateImage(dst_cvsize, img_ty->depth, img_ty->nChannels);
  261. IplImage *pic4 = cvCreateImage(dst_cvsize, img_ty->depth, img_ty->nChannels);
  262. IplImage *pic5 = cvCreateImage(dst_cvsize, img_ty->depth, img_ty->nChannels);
  263. IplImage *pic6 = cvCreateImage(dst_cvsize, img_ty->depth, img_ty->nChannels);
  264. IplImage *pic7 = cvCreateImage(dst_cvsize, img_ty->depth, img_ty->nChannels);
  265. IplImage* copy_zf = NULL;
  266. copy_zf = cvCloneImage( img_ty );
  267. CvRect ptx;
  268. ptx.x = ;
  269. ptx.y = ;
  270. ptx.height = ;
  271. ptx.width = ;
  272. cvSetImageROI(copy_zf, ptx);
  273. cvCopy(copy_zf, pic1);
  274. cvSaveImage("/home/panhao/QtProject/MyANPR/img/copy_zf1.jpg", pic1); //注意绝对路径 出错请debug
  275. pic1 = cvLoadImage("/home/panhao/QtProject/MyANPR/img/copy_zf1.jpg", ); //注意 这两句必须要,否则后面结果就不对
  276.  
  277. copy_zf = cvCloneImage( img_ty );
  278. ptx.x = +;
  279. ptx.y = ;
  280. ptx.height = ;
  281. ptx.width = ;
  282. cvSetImageROI(copy_zf, ptx);
  283. cvCopy(copy_zf, pic2);
  284. cvSaveImage("/home/panhao/QtProject/MyANPR/img/copy_zf2.jpg", pic2);
  285. pic2 = cvLoadImage("/home/panhao/QtProject/MyANPR/img/copy_zf2.jpg", );
  286.  
  287. copy_zf = cvCloneImage( img_ty );
  288. ptx.x = +++;
  289. ptx.y = ;
  290. ptx.height = ;
  291. ptx.width = ;
  292. cvSetImageROI(copy_zf, ptx);
  293. cvCopy(copy_zf, pic3);
  294. cvSaveImage("/home/panhao/QtProject/MyANPR/img/copy_zf3.jpg", pic3);
  295. pic3 = cvLoadImage("/home/panhao/QtProject/MyANPR/img/copy_zf3.jpg", );
  296.  
  297. copy_zf = cvCloneImage( img_ty );
  298. ptx.x = +++++;
  299. ptx.y = ;
  300. ptx.height = ;
  301. ptx.width = ;
  302. cvSetImageROI(copy_zf, ptx);
  303. cvCopy(copy_zf, pic4);
  304. cvSaveImage("/home/panhao/QtProject/MyANPR/img/copy_zf4.jpg", pic4);
  305. pic4 = cvLoadImage("/home/panhao/QtProject/MyANPR/img/copy_zf4.jpg", );
  306.  
  307. copy_zf = cvCloneImage( img_ty );
  308. ptx.x = +++++++;
  309. ptx.y = ;
  310. ptx.height = ;
  311. ptx.width = ;
  312. cvSetImageROI(copy_zf, ptx);
  313. cvCopy(copy_zf, pic5);
  314. cvSaveImage("/home/panhao/QtProject/MyANPR/img/copy_zf5.jpg", pic5);
  315. pic5 = cvLoadImage("/home/panhao/QtProject/MyANPR/img/copy_zf5.jpg", );
  316.  
  317. copy_zf = cvCloneImage( img_ty );
  318. ptx.x = +++++++++;
  319. ptx.y = ;
  320. ptx.height = ;
  321. ptx.width = ;
  322. cvSetImageROI(copy_zf, ptx);
  323. cvCopy(copy_zf, pic6);
  324. cvSaveImage("/home/panhao/QtProject/MyANPR/img/copy_zf6.jpg", pic6);
  325. pic6 = cvLoadImage("/home/panhao/QtProject/MyANPR/img/copy_zf6.jpg", );
  326.  
  327. copy_zf = cvCloneImage( img_ty );
  328. ptx.x = +++++++++++;
  329. ptx.y = ;
  330. ptx.height = ;
  331. ptx.width = ;
  332. cvSetImageROI(copy_zf, ptx);
  333. cvCopy(copy_zf, pic7);
  334. cvSaveImage("/home/panhao/QtProject/MyANPR/img/copy_zf7.jpg", pic7);
  335. pic7 = cvLoadImage("/home/panhao/QtProject/MyANPR/img/copy_zf7.jpg", );
  336.  
  337. //字符识别(使用模版逐点比对式,相似点*100/总点数=成功率)
  338. string wz_1 = db_successlv_1(pic1); //车牌第一个字符 以下以此类推 做返回值string中若有中文会有乱码
  339. string wz_2 = db_successlv_2(pic2);
  340. string wz_3 = db_successlv_3(pic3);
  341. string wz_4 = db_successlv_3(pic4);
  342. string wz_5 = db_successlv_4_7(pic5);
  343. string wz_6 = db_successlv_4_7(pic6);
  344. string wz_7 = db_successlv_4_7(pic7);
  345. string finish = wz_1 + wz_2 + wz_3 + wz_4 + wz_5 + wz_6 + wz_7; //最后结果
  346. //cout << "finish:"<<finish << endl;
  347. //printf("endl\n");
  348.  
  349. cvReleaseImage(&pic1);
  350. cvReleaseImage(&pic2);
  351. cvReleaseImage(&pic3);
  352. cvReleaseImage(&pic4);
  353. cvReleaseImage(&pic5);
  354. cvReleaseImage(&pic6);
  355. cvReleaseImage(&pic7);
  356. cvReleaseImage(&copy_zf);
  357. cvReleaseImage(&img_ty);
  358. cvReleaseImage(&ty_cpimg);
  359. cvReleaseImage(&pSrcImage);
  360. cvReleaseImage(&pGrayImage);
  361. cvReleaseImage(&pBinaryImage);
  362. cvReleaseImage(&cyp);
  363.  
  364. return finish;
  365. }
  366.  
  367. int sb_count_bd(IplImage *img)
  368. {
  369. int count = ;
  370. uchar *pt = (uchar *)img->imageData;
  371. const uchar step = img->widthStep;
  372. for(int w = ; w < img->width; w++)
  373. for(int h = ; h < img->height; h++)
  374. if(pt[h*step + w])
  375. count += w*h;
  376. return count;
  377. }
  378.  
  379. string db_successlv_3(IplImage *cs)
  380. {
  381. uchar *pt_cs = (uchar *)cs->imageData;
  382. uchar i = ;
  383. uchar max = ;
  384. uchar max_backup = ;
  385. uchar zf = ;
  386. string fhz = "\0";
  387. for(i = ; i < ; i++)
  388. {
  389. IplImage *mb = cvLoadImage(mb_ku_sf[i], );
  390. uchar cgl = ;
  391.  
  392. int cg_count = ;
  393. int bd_count = ;
  394. uchar *pt_mb = (uchar *)mb->imageData;
  395. const uchar step_cs = cs->widthStep;
  396. const uchar step_mb = mb->widthStep;
  397. for(int w = ; w < cs->width; w++)
  398. for(int h = ; h < cs->height; h++)
  399. {
  400. if((pt_cs[h*step_cs + w] == pt_mb[h*step_mb + w]))
  401. cg_count++;
  402. if(pt_mb[h*step_mb + w])
  403. bd_count++;
  404. }
  405. cvReleaseImage(&mb);
  406. cgl = (uchar)(((float)cg_count/(cs->height*cs->width))*);
  407. max = max<cgl? cgl : max;
  408. if(max != max_backup)
  409. zf = i;
  410. max_backup = max;
  411. }
  412. switch(zf)
  413. {
  414. case : fhz = "";break; case : fhz = "";break; case : fhz = "";break; case : fhz = "";break;
  415. case : fhz = "";break; case : fhz = "";break; case : fhz = "";break; case : fhz = "";break;
  416. case : fhz = "";break; case : fhz = "";break; case : fhz = "A";break; case : fhz = "B";break;
  417. case : fhz = "C";break; case : fhz = "D";break; case : fhz = "E";break; case : fhz = "F";break;
  418. case : fhz = "G";break; case : fhz = "H";break; case : fhz = "J";break; case : fhz = "K";break;
  419. case : fhz = "L";break; case : fhz = "M";break; case : fhz = "N";break; case : fhz = "P";break;
  420. case : fhz = "Q";break; case : fhz = "R";break; case : fhz = "S";break; case : fhz = "T";break;
  421. case : fhz = "U";break; case : fhz = "V";break; case : fhz = "W";break; case : fhz = "X";break;
  422. case : fhz = "Y";break; case : fhz = "Z";break;
  423. }
  424. return (fhz);
  425. }
  426.  
  427. string db_successlv_1(IplImage *cs)
  428. {
  429. string fhz = "\0";
  430. uchar *pt_cs = (uchar *)cs->imageData;
  431. uchar i = ;
  432. uchar max = ;
  433. uchar max_backup = ;
  434. uchar zf = ;
  435. for(i = ; i < ; i++)
  436. {
  437. IplImage *mb = cvLoadImage(mb_ku_zw[i], );
  438. uchar cgl = ;
  439.  
  440. int cg_count = ;
  441. int bd_count = ;
  442. uchar *pt_mb = (uchar *)mb->imageData;
  443. const uchar step_cs = cs->widthStep;
  444. const uchar step_mb = mb->widthStep;
  445. for(int w = ; w < cs->width; w++)
  446. for(int h = ; h < cs->height; h++)
  447. {
  448. if((pt_cs[h*step_cs + w] == pt_mb[h*step_mb + w]))
  449. cg_count++;
  450. if(pt_mb[h*step_mb + w])
  451. bd_count++;
  452. }
  453. cvReleaseImage(&mb);
  454. cgl = (uchar)(((float)cg_count/(cs->height*cs->width))*);
  455. max = max<cgl? cgl : max;
  456. if(max != max_backup)
  457. zf = i;
  458. max_backup = max;
  459. //printf("zf=%d\n",(int)zf);
  460. }
  461.  
  462. switch(zf)
  463. {
  464. case : fhz = "藏";break; case : fhz = "川";break; case : fhz = "鄂";break; case : fhz = "甘";break;
  465. case : fhz = "赣";break; case : fhz = "贵";break; case : fhz = "桂";break; case : fhz = "黑";break;
  466. case : fhz = "沪";break; case : fhz = "吉";break; case : fhz = "冀";break; case : fhz = "津";break;
  467. case : fhz = "晋";break; case : fhz = "京";break; case : fhz = "辽";break; case : fhz = "鲁";break;
  468. case : fhz = "蒙";break; case : fhz = "闽";break; case : fhz = "宁";break; case : fhz = "青";break;
  469. case : fhz = "琼";break; case : fhz = "陕";break; case : fhz = "苏";break; case : fhz = "皖";break;
  470. case : fhz = "湘";break; case : fhz = "新";break; case : fhz = "渝";break; case : fhz = "豫";break;
  471. case : fhz = "粤";break; case : fhz = "云";break; case : fhz = "浙";break;
  472. }
  473. //cout << "return"<<endl;
  474. return (fhz);
  475. }
  476.  
  477. string db_successlv_2(IplImage *cs)
  478. {
  479. string fhz = "\0";
  480. uchar *pt_cs = (uchar *)cs->imageData;
  481. uchar i = ;
  482. uchar max = ;
  483. uchar max_backup = ;
  484. uchar zf = ;
  485. for(i = ; i < ; i++)
  486. {
  487. IplImage *mb = cvLoadImage(mb_ku_zf[i], );
  488. uchar cgl = ;
  489.  
  490. int cg_count = ;
  491. int bd_count = ;
  492. uchar *pt_mb = (uchar *)mb->imageData;
  493. const uchar step_cs = cs->widthStep;
  494. const uchar step_mb = mb->widthStep;
  495. for(int w = ; w < cs->width; w++)
  496. for(int h = ; h < cs->height; h++)
  497. {
  498. if((pt_cs[h*step_cs + w] == pt_mb[h*step_mb + w]))
  499. cg_count++;
  500. if(pt_mb[h*step_mb + w])
  501. bd_count++;
  502. }
  503. cvReleaseImage(&mb);
  504. cgl = (uchar)(((float)cg_count/(cs->height*cs->width))*);
  505. max = max<cgl? cgl : max;
  506. if(max != max_backup)
  507. zf = i;
  508. max_backup = max;
  509. //printf("wz_2 i=%d,zf=%d,max=%d\n",(int)i,(int)zf,(int)max);
  510. }
  511. switch(zf)
  512. {
  513. case : fhz = "A";break; case : fhz = "B";break;
  514. case : fhz = "C";break; case : fhz = "D";break; case : fhz = "E";break; case : fhz = "F";break;
  515. case : fhz = "G";break; case : fhz = "H";break; case : fhz = "J";break; case : fhz = "K";break;
  516. case : fhz = "L";break; case : fhz = "M";break; case : fhz = "N";break; case : fhz = "P";break;
  517. case : fhz = "Q";break; case : fhz = "R";break; case : fhz = "S";break; case : fhz = "T";break;
  518. case : fhz = "U";break; case : fhz = "V";break; case : fhz = "W";break; case : fhz = "X";break;
  519. case : fhz = "Y";break; case : fhz = "Z";break;
  520. }
  521. return (fhz);
  522. }
  523.  
  524. string db_successlv_4_7(IplImage *cs)
  525. {
  526. string fhz = "\0";
  527. uchar *pt_cs = (uchar *)cs->imageData;
  528. uchar i = ;
  529. uchar max = ;
  530. uchar max_backup = ;
  531. uchar zf = ;
  532. for(i = ; i < ; i++)
  533. {
  534. IplImage *mb = cvLoadImage(mb_ku_sz[i], );
  535. uchar cgl = ;
  536.  
  537. int cg_count = ;
  538. int bd_count = ;
  539. uchar *pt_mb = (uchar *)mb->imageData;
  540. const uchar step_cs = cs->widthStep;
  541. const uchar step_mb = mb->widthStep;
  542. for(int w = ; w < cs->width; w++)
  543. for(int h = ; h < cs->height; h++)
  544. {
  545. if((pt_cs[h*step_cs + w] == pt_mb[h*step_mb + w]))
  546. cg_count++;
  547. if(pt_mb[h*step_mb + w])
  548. bd_count++;
  549. }
  550. cvReleaseImage(&mb);
  551. cgl = (uchar)(((float)cg_count/(cs->height*cs->width))*);
  552. max = max<cgl? cgl : max;
  553. if(max != max_backup)
  554. zf = i;
  555. max_backup = max;
  556. }
  557. switch(zf)
  558. {
  559. case : fhz = "";break; case : fhz = "";break; case : fhz = "";break; case : fhz = "";break;
  560. case : fhz = "";break; case : fhz = "";break; case : fhz = "";break; case : fhz = "";break;
  561. case : fhz = "";break; case : fhz = "";break;
  562. }
  563. return (fhz);
  564. }

char

前面的路径中就是字符库的图片路径。

最后可以得到车牌号码的 字符串,接下来就是后台的处理。

3.对进出用户的信息存储和读取。

这里我们使用的是Qt界面程序语言编写的客户端。

这里是真正的发挥空间,可以使用得来的数据进行存储,还有手机客户端给用户信息。

 

 

基于opencv的车牌识别系统的更多相关文章

  1. python基于OpenCV的人脸识别系统

    想获得所有的代码,请下载(来自我的CSDN): https://download.csdn.net/download/qq_40875849/11292912 主函数: from recognitio ...

  2. EasyPR--中文开源车牌识别系统 开发详解(1)

    在上篇文档中作者已经简单的介绍了EasyPR,现在在本文档中详细的介绍EasyPR的开发过程. 正如淘宝诞生于一个购买来的LAMP系统,EasyPR也有它诞生的原型,起源于CSDN的taotao123 ...

  3. EasyPR--一个开源的中文车牌识别系统

    我正在做一个开源的中文车牌识别系统,Git地址为:https://github.com/liuruoze/EasyPR. 我给它取的名字为EasyPR,也就是Easy to do Plate Reco ...

  4. 基于 OpenCV 的人脸识别

    基于 OpenCV 的人脸识别 一点背景知识 OpenCV 是一个开源的计算机视觉和机器学习库.它包含成千上万优化过的算法,为各种计算机视觉应用提供了一个通用工具包.根据这个项目的关于页面,OpenC ...

  5. 数字图像处理:基于MATLAB的车牌识别项目 标签: 图像处理matlab算法 2017-06-24 09:17 98人阅读 评论(0)

    学过了数字图像处理,就进行一个综合性强的小项目来巩固一下知识吧.前阵子编写调试了一套基于MATLAB的车牌识别的项目的代码.今天又重新改进了一下代码,识别的效果好一点了,也精简了一些代码.这里没有使用 ...

  6. 基于ARM的车牌识别技术研究与实现

    在云盘里包含了我本科毕业设计的全部资料和代码.主要涉及下面摘要中的几个部分.虽然系统无法实用,但是适合机器视觉和嵌入式方向的入门.希望能对有志从事相关方向的朋友有所帮助.本人现在在深圳从事机器视觉算法 ...

  7. 【计算机视觉】基于OpenCV的人脸识别

    一点背景知识 OpenCV 是一个开源的计算机视觉和机器学习库.它包含成千上万优化过的算法,为各种计算机视觉应用提供了一个通用工具包.根据这个项目的关于页面,OpenCV 已被广泛运用在各种项目上,从 ...

  8. java基于OpenCV的人脸识别

    基于Java简单的人脸和人眼识别程序 使用这个程序之前必须先安装配置OpenCV详细教程见:https://www.cnblogs.com/prodigal-son/p/12768948.html 注 ...

  9. 毕业设计 python opencv实现车牌识别 界面

    主要代码参考https://blog.csdn.net/wzh191920/article/details/79589506 GitHub:https://github.com/yinghualuow ...

随机推荐

  1. Gradle之恋-任务1

    任务作为Gradle的核心功能模块,而且Gradle的任务还可以具有自己的属性和方法,大大扩展了Ant任务的功能.由于任务相关内容比较多,分为两篇来探讨,本篇主要涉及到:任务的定义.任务的属性.任务的 ...

  2. Oracle Developer Data Modeler项目实践 (转)

    http://www.Oracle.com/webfolder/technetwork/tutorials/obe/db/sqldevdm/r30/datamodel2moddm/datamodel2 ...

  3. Struts2中Action配置的三种方式

    <!-- 方案一:一个action对应一个方法; --> <action name="add" class="com.gxxy.struts.kp03_ ...

  4. 3713: [PA2014]Iloczyn

    3713: [PA2014]Iloczyn Time Limit: 1 Sec  Memory Limit: 128 MBSubmit: 327  Solved: 181[Submit][Status ...

  5. 1657: [Usaco2006 Mar]Mooo 奶牛的歌声

    1657: [Usaco2006 Mar]Mooo 奶牛的歌声 Time Limit: 5 Sec  Memory Limit: 64 MBSubmit: 526  Solved: 365[Submi ...

  6. C++ Primer 5 CH2 变量和基本类型

    C++ 是一种静态数据类型语言,它的类型检查发生在编译时.因此,编译器需要知道每一个变量对应的数据类型. 2.1 基本内置类型 算术类型 C++ 标准并没有规定带符号类型应如何表示,但是约定了在表示范 ...

  7. MySQL基准测试(benchmark)

    基准测试是唯一方便有效的.可以学习系统在给定的工作负载下会发生什么的方法.基准测试可以观察系统在不同压力下的行为,评估系统的容量,掌握哪些是重要的变化,或者观察系统如何处理不同的数据. 验证基于系统的 ...

  8. cobbler自动安装系统

    一.简介 Cobbler是一个快速网络安装linux的服务,而且在经过调整也可以支持网络安装windows.该工具使用python开发,小巧轻便(才15k行python代码),使用简单的命令即可完成P ...

  9. 2017-3-20 HTML 基础知识

    HTML的定义:HTML是一门编程语言的名字:超文本标记语言(Hyper Text Mark-up Language ),就是超越了文字的范畴,除了文字还可以有图片.视频.音频.动画.特效.表格.链接 ...

  10. elasticsearch 索引 red 状态恢复 green

    方案一 找到状态为 red 的索引 curl -X GET "http://172.xxx.xxx.174:9288/_cat/indices?v=" red open index ...