matlab一维条形码码字识别程序.docx
《matlab一维条形码码字识别程序.docx》由会员分享,可在线阅读,更多相关《matlab一维条形码码字识别程序.docx(11页珍藏版)》请在冰豆网上搜索。
matlab一维条形码码字识别程序
closeall
I=imread('E:
\');
J=rgb2gray(I);
figure
(1)
imshow(J);
title('灰度化图像');
[e1,e2]=size(J);
Im=imcrop(J,[e2/2-200,e1/2-200,400,400]);
figure
(2)
subplot(1,2,1),imshow(Im)
title('中心区域');
subplot(1,2,2),imhist(Im)
title('中心区域直方图');
[xa,ya]=size(Im);
b=double(Im);
zd=double(max(Im));
zx=double(min(Im));
T=double((zd+zx))/2;
count=double(0);
while1
count=count+1;
S0=;n0=;
S1=;n1=;
fori=1:
xa
forj=1:
ya
ifdouble(Im(i,j))>=T
S1=S1+double(Im(i,j));
n1=n1+1;
else
S0=S0+double(Im(i,j));
n0=n0+1;
end
end
end
T0=S0/n0;
T1=S1/n1;
ifabs(T-((T0+T1)/2))<
break;
else
T=(T0+T1)/2;
end
end
count
T
K=find(JJ(K)=0;
K=find(J>=T);
J(K)=255;
figure(3)
imshow(J)
title('图像二值化');
B=medfilt2(J,[5,1]);
figure(4)
imshow(B)
title('中值滤波后图像');
[y0,x0]=size(B);
BW=edge(B,'log');
figure(5);imshow(BW);title('边缘检测图像')
%functioncode=barcode(pic)%条形码识别
check_left=[13,25,19,61,35,49,47,59,55,11;...%左边数据编码,奇
39,51,27,33,29,57,5,17,9,23];%左边数据编码,偶
check_right=[114,102,108,66,92,78,80,68,72,116];%右边数据编码
first_num=[31,20,18,17,12,6,3,10,9,5];%第一位数据编码
bar=imread('E:
\');%读输入条形码图片
bar_Gray=rgb2gray(bar);%将RGB图片转换灰度图
[a_histx]=imhist(bar_Gray);
hist_max=[];
ifa_hist
(1)>a_hist
(2)
hist_max=[hist_max1];
end
x=max(x);
fori=2:
x
ifa_hist(i)>a_hist(i-1)&&a_hist(i)>a_hist(i+1)
hist_max=[hist_maxi];
end
end
ifa_hist(x)hist_max=[hist_maxx+1];
end
[m,n]=size(hist_max);
k=0;
max_1=0;
max_2=0;
fori=1:
n
ifkk=a_hist(hist_max(i));
max_1=hist_max(i);
end
end
temp=a_hist(max_1);
a_hist(max_1)=0;
k=0;
fori=1:
n
ifkk=a_hist(hist_max(i));
max_2=hist_max(i);
end
end
a_hist(max_1)=temp;
ifmax_1>max_2
k=max_1;
max_1=max_2;
max_2=k;
end
T=max_1;
k=a_hist(max_1);
fori=max_1:
max_2
ifk>a_hist(i)
k=a_hist(i);
T=i;
end
end
[m,n]=size(bar_Gray);%求灰度图的大小
fori=1:
m%对图像进行二值化处理
forj=1:
n
ifbar_Gray(i,j)>T%选择适当的阈值进行二值化处理
bar_10(i,j)=1;
else
bar_10(i,j)=0;
end
end
end
%imshow(bar_10);
l=0;%检测59根条形码
fori=1:
m
k=1;
l=l+1;
forj=1:
n-1
ifbar_10(i,j)~=bar_10(i,j+1)%比较同一行相邻两点的颜色是否一致
%bar_x(l,k)=i;
bar_y(l,k)=j;%记录转折点的纵坐标
k=k+1;%准备记录下一个数据点
end
ifk>61%点数大于60,该行应该删掉
l=l-1;
break
end
end
ifk<61%点数小于60,该行应该删掉
l=l-1;
end
end
[m,n]=size(bar_y);
ifm<=1%查看条形码是否有效
code='0';
fprintf(1,'GameOver!
\n');
return
end
fori=1:
m%计算每根条形码的宽度
forj=1:
n-1
bar_num(i,j)=bar_y(i,j+1)-bar_y(i,j);
ifbar_num(i,j)<0
bar_num(i,j)=0;
end
end
end
bar_sum=sum(bar_num)/m;%求每根条形码宽度的平均值
k=0;
fori=1:
59%计算59根条形码的总宽度
k=k+bar_sum(i);
end
k=k/95;%计算单位条形码的宽度
fori=1:
59%计算每根条形码所占位数
bar_int(i)=round(bar_sum(i)/k);
end
k=1;
fori=1:
59%将条形码转换成二进制数
ifrem(i,2)
forj=1:
bar_int(i)%黑色条用1表示
bar_01(k)=1;
k=k+1;
end
else
forj=1:
bar_int(i)%白色条用0表示
bar_01(k)=0;
k=k+1;
end
end
end
if((bar_01
(1)&&~bar_01
(2)&&bar_01(3))...%判断起始符是否正确
&&(~bar_01(46)&&bar_01(47)&&~bar_01(48)&&bar_01(49)&&~bar_01(50))...%判断中间分隔符是否正确
&&(bar_01(95)&&~bar_01(94)&&bar_01(93)))%判断终止符是否正确
l=1;
fori=1:
6%将左侧42位二进制数转换为十进制数
bar_left(l)=0;
fork=1:
7
bar_left(l)=bar_left(l)+bar_01(7*(i-1)+k+3)*(2^(7-k));
end
l=l+1;
end
l=1;
fori=1:
6%将右侧42位二进制数转换为十进制数
bar_right(l)=0;
fork=1:
7
bar_right(l)=bar_right(l)+bar_01(7*(i+6)+k+1)*(2^(7-k));
k=k-1;
end
l=l+1;
end
end
num_bar='';
num_first=0;
first=2;
fori=1:
6%从左边数据编码表中查出条形码编码数字
forj=0:
1
fork=0:
9
ifbar_left(i)==check_left(j+1,k+1)
num_bar=strcat(num_bar,num2str(k));
switchfirst%记录左边数据的奇偶顺序
case2
first=j;
break;
case1
num_first=num_first+j*(2^(6-i));
break;
case0
num_first=num_first+~j*(2^(6-i));
break;
otherwise
break;
end
end
end
end
end
fori=1:
6%从右边数据编码表中查出条形码编码数字
forj=0:
9
ifbar_right(i)==check_right(j+1)
num_bar=strcat(num_bar,num2str(j));
end
end
end
fori=0:
9%从第一位数据编码表中查出第一位数字
ifnum_first==first_num(i+1)
num_bar=strcat(num2str(i),num_bar);
break;
end
end
ifnumel(num_bar)~=13
fprintf(1,'PleaseTurnItAround!
\n');
return
end
check_code=0;
fori=1:
12%计算校验码
ifrem(i,2)
check_code=check_code+str2double(num_bar(i));
else
check_code=check_code+str2double(num_bar(i))*3;
end
end
check_code=rem(check_code,10);
ifcheck_code>0
check_code=10-check_code;
end
ifcheck_code==str2double(num_bar(13))%判断校验码是否正确
code=num_bar;
else
fprintf(1,'PleaseTurnItAround!
\n');
return
end