OpenCV的基础光学字符识别Basic OCR in OpenCV.docx
- 文档编号:2794841
- 上传时间:2022-11-15
- 格式:DOCX
- 页数:12
- 大小:69.09KB
OpenCV的基础光学字符识别Basic OCR in OpenCV.docx
《OpenCV的基础光学字符识别Basic OCR in OpenCV.docx》由会员分享,可在线阅读,更多相关《OpenCV的基础光学字符识别Basic OCR in OpenCV.docx(12页珍藏版)》请在冰豆网上搜索。
OpenCV的基础光学字符识别BasicOCRinOpenCV
Github源码
From:
在这个教程当中我们将完成一个基础的数字光学字符识别。
这包括把一个手写的数字分类进它所属的类里。
为了完成它,们我将要使用我们之前的教程里所有学到的东西,我们将要使用简单的 basicpainter 和 thebasicpatternrecognitionandclassificationwithopenCV 两个教程。
在一个典型的模式识别分类器里,包括三个模块:
预处理(信号获取和滤波)
特征提取(特征向量的计算)
分类(特征向量的分类)
预处理(Preprocessing):
在这个模块我们将要处理我们输入的图片,比如大小标准化,彩色图像灰度化等等。
特征提取(Featureextraction):
在这个模块我们转换我们处理后的图像为一个特征向量以便于分类,它可能是像素矩阵转换成向量或者获取轮廓编码链的数据表示。
分类模块获取特征向量,并训练我们的系统或者说使用一个分类方法(比如knn)把输入的特征向量分类。
这个基础光学字符识别的流程图如下:
现在我们有由图片组成的一个训练集和一个测试集来训练和测试我们的分类器(knn)。
我们有1000张手写数字的图片,每个数字100张。
我们使用每个数字的50张图片来训练,另外50张来测试我们的系统。
接下来我们要做的第一个工作就是对所有训练集的图片预处理,为了完成它我们创建一个预处理函数。
在这个函数中,我们输入一张图片和我们想要它在处理后得到的新的长和宽,这个函数讲返回一个标准大小的带有边框的图片。
你可以看到更多清楚的处理流程:
预处理代码:
voidfindX(IplImage*imgSrc,int*min,int*max){
inti;
intminFound=0;
CvMatdata;
CvScalarmaxVal=cvRealScalar(imgSrc->width*255);
CvScalarval=cvRealScalar(0);
//Foreachcolsum,ifsum //thencontinuetoendtosearchthemax,ifsum for(i=0;i cvGetCol(imgSrc,&data,i); val=cvSum(&data); if(val.val[0] *max=i; if(! minFound){ *min=i; minFound=1; } } } } voidfindY(IplImage*imgSrc,int*min,int*max){ inti; intminFound=0; CvMatdata; CvScalarmaxVal=cvRealScalar(imgSrc->width*255); CvScalarval=cvRealScalar(0); //Foreachcolsum,ifsum //thencontinuetoendtosearchthemax,ifsum for(i=0;i cvGetRow(imgSrc,&data,i); val=cvSum(&data); if(val.val[0] *max=i; if(! minFound){ *min=i; minFound=1; } } } } CvRectfindBB(IplImage*imgSrc){ CvRectaux; intxmin,xmax,ymin,ymax; xmin=xmax=ymin=ymax=0; findX(imgSrc,&xmin,&xmax); findY(imgSrc,&ymin,&ymax); aux=cvRect(xmin,ymin,xmax-xmin,ymax-ymin); //printf("BB: %d,%d-%d,%d\n",aux.x,aux.y,aux.width,aux.height); returnaux; } IplImagepreprocessing(IplImage*imgSrc,intnew_width,intnew_height){ IplImage*result; IplImage*scaledResult; CvMatdata; CvMatdataA; CvRectbb;//boundingbox CvRectbba;//boundinbboxmaintainaspectratio //Findboundingbox bb=findBB(imgSrc); //Getboundingboxdataandnowithaspectratio,thexandycanbecorrupted cvGetSubRect(imgSrc,&data,cvRect(bb.x,bb.y,bb.width,bb.height)); //Createimagewiththisdatawithwidthandheightwithaspectratio1 //thenwegethighestsizebetwenwidthandheightofourboundingbox intsize=(bb.width>bb.height)? bb.width: bb.height; result=cvCreateImage(cvSize(size,size),8,1); cvSet(result,CV_RGB(255,255,255),NULL); //Copydedataincenterofimage intx=(int)floor((float)(size-bb.width)/2.0f); inty=(int)floor((float)(size-bb.height)/2.0f); cvGetSubRect(result,&dataA,cvRect(x,y,bb.width,bb.height)); cvCopy(&data,&dataA,NULL); //Scaleresult scaledResult=cvCreateImage(cvSize(new_width,new_height),8,1); cvResize(result,scaledResult,CV_INTER_NN); //Returnprocesseddata return*scaledResult; } 我们使用basicOCR类的getData函数来创建训练数据和训练类,这个函数获取所有在OCR文件夹下的图片来创建训练数据,OCR文件夹中的每个类是一个文件夹,其中每个文件都是名为cnn.pbm的pbm文件,c是类(0,1,...,9)中的一个,nn是图片的编号(00,01,...,99)。 我们得到的每张图片都是预处理过的了,然后他们将转换成特征向量里的数据以便我们使用。 basicOCR.cpp获取数据代码: voidbasicOCR: : getData() { IplImage*src_image; IplImageprs_image; CvMatrow,data; charfile[255]; inti,j; for(i=0;i for(j=0;j //Loadfile if(j<10) sprintf(file,"%s%d/%d0%d.pbm",file_path,i,i,j); else sprintf(file,"%s%d/%d%d.pbm",file_path,i,i,j); src_image=cvLoadImage(file,0); if(! src_image){ printf("Error: Cantloadimage%s\n",file); //exit(-1); } //processfile prs_image=preprocessing(src_image,size,size); //Setclasslabel cvGetRow(trainClasses,&row,i*train_samples+j); cvSet(&row,cvRealScalar(i)); //Setdata cvGetRow(trainData,&row,i*train_samples+j); IplImage*img=cvCreateImage(cvSize(size,size),IPL_DEPTH_32F,1); //convert8bitsimageto32floatimage cvConvertScale(&prs_image,img,0.0039215,0); cvGetSubRect(img,&data,cvRect(0,0,size,size)); CvMatrow_header,*row1; //convertdatamatrixsizexsizetovecor row1=cvReshape(&data,&row_header,0,1); cvCopy(row1,&row,NULL); } } } 在处理并且得到训练数据和类以后我们用我们的模型训练这些数据,在这个例子中我们用knn方法: knn=newCvKNearest(trainData,trainClasses,0,false,K); 现在我们可以测试我们的模型了,并且我们可以使用测试的结果来和其它我们使用的方法比较,又或者我们减小图片大小等等。 这里是在我们的basicOCR类里创建的一个函数,测试函数。 这个函数获取其它500个样本并且用我们选择的方法分类,再检验得到的结果。 voidbasicOCR: : test(){ IplImage*src_image; IplImageprs_image; CvMatrow,data; charfile[255]; inti,j; interror=0; inttestCount=0; for(i=0;i for(j=50;j<50+train_samples;j++){ sprintf(file,"%s%d/%d%d.pbm",file_path,i,i,j); src_image=cvLoadImage(file,0); if(! src_image){ printf("Err
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- OpenCV的基础光学字符识别Basic OCR in OpenCV 基础 光学 字符 识别 Basic