MATLAB简易验证码识别程序介绍
Posted jins-note
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了MATLAB简易验证码识别程序介绍相关的知识,希望对你有一定的参考价值。
本推文主要识别的验证码是这种:
![技术分享图片](https://image.cha138.com/20210807/94e2efd9e35941f8a510c9d73443fc5b.jpg)
![技术分享图片](https://image.cha138.com/20210807/55b02612104b4500aefcaa4146f0b4f0.jpg)
![技术分享图片](https://image.cha138.com/20210807/715d44732a3441ef92b34f11e851907d.jpg)
第一步: 二值化
所谓二值化就是把不需要的信息通通去除,比如背景,干扰线,干扰像素等等,只剩下需要识别的文字,让图片变成2进制点阵。
![技术分享图片](https://image.cha138.com/20210807/d4fcd6028c7642fe9fb9e6383505c127.jpg)
![技术分享图片](https://image.cha138.com/20210807/ea22b40fdeed4c42b29db2e1def66f44.jpg)
![技术分享图片](https://image.cha138.com/20210807/f601bf74df8e4deab3ea54ef7e9f153d.jpg)
第二步: 文字分割
为了能识别出字符,需要对要识别的文字图图片进行分割,把每个字符作为单独的一个图片看待。
![技术分享图片](https://image.cha138.com/20210807/9ad198d0ab8b491398a9a45ecdf4517d.jpg)
![技术分享图片](https://image.cha138.com/20210807/cafe16bf8dd9444b8e64b69358a1a518.jpg)
![技术分享图片](https://image.cha138.com/20210807/1b1f06ae7a464af3a29bda56f5752ab6.jpg)
![技术分享图片](https://image.cha138.com/20210807/72a774eb4cc64f6e90d8d62f45c14e53.jpg)
![技术分享图片](https://image.cha138.com/20210807/766bf5b0060e430f9d90cdda6a6c41a1.jpg)
![技术分享图片](https://image.cha138.com/20210807/080d89dca1b544b992e6530889179a65.jpg)
![技术分享图片](https://image.cha138.com/20210807/8c7a7242804f4ea3b9749d4ad3c6e331.jpg)
![技术分享图片](https://image.cha138.com/20210807/5de5aa833b90499ca0ff0cde87b43a00.jpg)
![技术分享图片](https://image.cha138.com/20210807/385e19647c534f7e8d42a0cabe8adb4a.jpg)
![技术分享图片](https://image.cha138.com/20210807/0fa836682f7943eb8c791ea869a6d2a3.jpg)
![技术分享图片](https://image.cha138.com/20210807/9442a0a8d15144e4928adf210cac43a3.jpg)
第三步: 标准化
对于部分特殊的验证码,需要对分割后的图片进行标准化处理,也就是说尽量把每个相同的字符都变成一样的格式,减少随机的程度。最简单的比如旋转还原,复杂点的比如扭曲还原等等。比如本文中分割后的数字1和8宽度不一致,把他们的宽度填充一致,就是标准化的一种。
可以看到上面切割后的字符1最右边一列像素都为0。
第四步: 学习 & 识别
这一步可以用很多种方法,最简单的就是模板对比,对每个出现过的字符进行处理后把点阵变成字符串,标明是什么字符后,通过字符串对比来判断相似度。
在文章的后半部分会详细解释我采用的算法。
训练集学习tran.m
width = 132; height = 20; %共10张验证码 x 11个数字 共分割出 110张字符图片 %每个字符图片 高度20 x 宽度9 共 180个像素 data = zeros(110, 180); chars = zeros(180, 10); %用于存储10个数字字符的特征值 每个字符大小为20x9 for name = 0:9 im = imread(sprintf(‘%d.jpg‘, name)); %读取图片 im = im2bw(im) == 0; %第一步:二值化 黑色1 白色0 %第二步: 分割 black = sum(im) ~= 0; %20x132矩阵 从上向下求和为 1x132 不等于0 则横坐标对应的一列有字符像素 white = sum(im) == 0; %20x132矩阵 从上向下求和为 1x132 等于0 则横坐标对应的一列没有字符像素 lower = find(min([black 0],[1 white])); %获取11个字符的开始下标 upper = find(min([0 black],[white 1])) - 1; %获取11个字符的结束下标 for i=1:11 ch = im(:,lower(i):upper(i)); %截取单个字符 ch(20, 9) = 0; %第三步: 字符二值化矩阵大小标准化为20x9 data(name*11 + i ,:) = ch(:); %字符图片数据存入data end end %第四步: 学习 & 识别 class = clusterdata(data, 10); %将110个字符图片分为10类 %各个分类号对应的实际数字(人工识别后写进去的- -) num = [5 3 6 8 9 0 7 2 1 4]; for i = 1:10 %各类中的字符图片取均值 im = mean(data(class == i, :)) > 0.5; chars(:, num(i) + 1) = im; %存储 end
验证码识别ocr.m
function ret = ocr(filename) load; ret = zeros(1, 11); im = imread(filename); im = im2bw(im) == 0; %第一步: 二值化 %第二步: 分割 black = sum(im) ~= 0; white = sum(im) == 0; lower = find(min([black 0],[1 white])); upper = find(min([0 black],[white 1])) - 1; for i=1:11 ch = im(:,lower(i):upper(i)); ch = ch(:); ch(180) = 0; %第三步标准化 %第四步: 识别 [~, num] = max(sum(min(repmat(ch, 1, 10), chars))); ret(i) = num-1; end end
以上是关于MATLAB简易验证码识别程序介绍的主要内容,如果未能解决你的问题,请参考以下文章