MATLAB指纹识别系统GUI界面实现
- 课题背景
人的指纹各不相同,指纹可以用来确定人的身份,指纹识别技术作为最传统、最成熟的生物识别方式之一,已经在很多领域得以应用。如何对指纹的基本特征进行有效提取制约着指纹识别技术的发展。对指纹的特征进行更为完善、精准、简洁地表示是我们当前最重要的任务,只有做好这一步,才能使得指纹匹配进行的更加顺利,指纹识别技术有质的飞跃。
二、算法流程
对指纹的基本特征进行描述采取以下算法,如图6.1所示:
1图像预处理阶段
优秀的指纹图像预处理方法能够修复图像采集中的指纹线条信息的丢失,减小指纹传感器采集高质量指纹图像的压力,同时能够为下一步的特征点提取提供一幅完整的局部指纹图像。
2 切割
切割是指将不需要计算的空白的地方切去,可以使后面的计算点大大减少以提高处理的速度,切割的算法是分别从四边进行逐行(逐列)的扫描,遇到像素值不等于255的则退出当前方向的切割,否则将这一行切去。(详情见代码1)
处理前 处理后
3均衡化处理
指纹图像的灰度变换就是对指纹图像进行点运算。对于一幅输入图
像,经过点运算将产生一幅输出图像,后者的每个像素点的灰度值仅由相
应输入像素点的灰度值决定。点运算不改变图像内的空间关系。通过点运
算可以扩展图像中感兴趣部分的对比度,因而有时也称为对比度增强。
图像均衡化的目的就是增加灰度图像的对比度。[1]
并且在这里将整个图像分成了8x8的小块,分块进行处理
计算公式为:(详情见代码2)
某点处像素新值=255x小于等于该点处像素灰度值的象素数量/图像所有像素数量
处理结果:
4归一化处理与二值化处理
一:归一化
为了实现对不同灰度值的图像进行统一处理,需要对图像进行归一化处理。归一化处理的目的是调整指纹图像的灰度均值和方差接近期望均值M0,V0。归一化不改变脊线和谷线的清晰度,但可以减少沿着脊线和谷线方向上灰度的变化。
二、值化
(1)二值化的定义
二值化处理即对指纹图像中像素的灰度值与阈值进行比较判断,从而把灰度值变为 0 或 255,其中0表示脊线子图,255表示背景子图,就是把灰度图像变为黑白图像的过程。
(2)阈值的计算
本题采用了局部阈值法中的分块均值法。由于指纹图像的特点是纹线和谷线交错有序地排列,纹线和谷线上的点的数量大致相当,因此,简单地求取灰度平均值即可得到分块区域的阈值。
二值化处理前的图像 二值化处理后的图像
5 细化并且去除毛刺处理阶段
图像细化就是将峭的宽度降为单个像素的宽度,得到峭线的骨架图像的过程。这个过程进一步减少了图像数据量,清晰化了峭线形态,为之后的特征值提取作好准备。由于我们所关心的不是峭线的粗细,而是峭线的有无。因此,在不破坏图像连通性的情况下必须去掉多余的信息。因而应先将指纹峭线的宽度采用逐渐剥离的方法,使得峭线成为只有一个象素宽的细线,这将非常有利于下一步分析。
而毛刺,带有非常短的分支而被误认为是分叉。认识到合法的和不合法的节点后,在特征提取阶段排除这些节点。指纹图像预处理的目的主要是为特征值提取的有效性、准确性作好准备。
最终得到细化图像如图6.5所示。
图6.5细化处理后图像相对于指纹图像的二值化来说,指纹图像的细化大大减少了指纹图像的存储空间,去除了大量的冗余信息,提高了指纹识别的效率。
5 特征提取阶段
指纹特征点在二值化和细化之后,会有着一些较为明显的拓扑性质。本阶段,通过分析指纹特征点的拓扑形状,总结出提取指纹特征点的公式。然后,通过对指纹图像细化后的脊线上的像素点计算该公式,完成指纹图像特征提取工作。
(1)端点提取
由于指纹图像已经进行了二值化和细化的处理,每一点的灰度值只能为 0 或 255,本文则以待检测点为中心,以一个像素距离的 8 个点为边界建立 8 象限模板图形。如图6.6所示,图像正中间的 A 点即为待检测点。如果待测点为端点,则其满足此 8 象限模板图形中相邻像素点灰度值之差的绝对值为 2*255。
A
图6.5指纹实际纹线端点(左)和端点 8 像素模型(右)
具体的提取方法为:扫描某一待测点,如果其周围相邻的 8 个点两两灰度值之差的绝对值之和为 2*255,则此点即为端点。
(2)分叉点提取
由于指纹图像已经进行了二值化和细化的处理,每一点的灰度值只能为 0 或 255,本文则以待检测点为中心,以一个像素距离的 8 个点为边界建立 8 象限模板图形。如图6.6所示,图像正中间的黑点即为待检测点,如果待测点为分叉点,则其满足此 8 象限模板图形中相邻点像素灰度值之差的绝对值为 2*255。
B
图6.6指纹实际纹分叉点(左)和分叉点 8 象限模型(右)
具体的提取方法为:扫描某一待测点,如果其周围相邻的 8 个点两两灰度值之差的绝对值之和为 6*255,则此点即为分叉点。
其中提取的主要算法是:
(abs(f(i-1,j+1)-f(i,j+1))+abs(f(i-1,j)-f(i-1,j+1))+abs(f(i-1,j-1)-f(i-1,j))+abs(f(i,j-1)-f(i-1,j-1))+abs(f(i+1,j-1)-f(i,j-1))+abs(f(i+1,j)-f(i+1,j-1))+abs(f(i+1,j+1)-f(i+1,j))+abs(f(i,j+1)-f(i+1,j+1))==6)&(f(i-1,j+1)+f(i,j+1)+f(i-1,j)+f(i-1,j-1)+f(i,j-1)+f(i+1,j-1)+f(i+1,j)+f(i+1,j+1)==5)
(详情见代码6)
7进一步压缩字节数
为了使得字节数更少,存储更加精简,我们对表示方案进行改进,在图像预处理之前对指纹图像进行归一化和均衡化处理,这样使得指纹的无用信息进一步减少,从而使得指纹的存储更加精简。
并且通过条件控制特征值提取的数量。
经过以上步骤,实现了对指纹的特征提取,经验证,表示方法小于200字节。
8“指纹密码”的唯一性
经过实验验证,指纹密码可由指纹唯一确定。
9比较不同指纹的异同及相似程度
将比较不同指纹的异同及相似程度转化为指纹匹配问题。
9.1指纹数字图像匹配过程
在指纹数字图像匹配之前,要先提取出指纹数字图像的中间点,再建立特征模板,这些都是为指纹数字图像进行匹配做的准备工作。
9.2 中间点定位
中间点是指指纹数字图像的脊曲线曲率最大的点,在本文的匹配算法中,将中间点作为匹配参考点。这里选取的中间是指纹数字图像中间的一个小范围,先求出指纹数字图像的点方位,相邻 8 个灰度数值之和的平均数值,再求这 8 个灰度数值与平均数值之差的和,最小的所在的方位即此点所在指纹数字图像脊线的。
方位,从而得到点方位图。把点方位图分为 16×16 大小的小块,对每块计算直方图,其峰数值方位即为块方位,即每块中点的主导方位。然后在这个粗的块方位图上按照以下原则去搜索中间范围,逐行检查块方位数组。然后再根据求出各个方位的角度以及相邻 8 个灰度数值之和的平均数值,再求这 8 个灰度数值与平均数值之差的和,最小的所在的方位即此点所在指纹数字图像脊线的方位,这样就得到了点方位图。
9.3建立特征模板
如前所述,端点及交叉点是指纹细化图像的主要特征,我们可以采用这两种主要特征来构造指纹的特征向量模板。特征端点分类为 1,特征分叉点分类为 2;建立特征端点相对中间点的距离向量,和特征分叉点相对中间点的距离向量;建
立特征端点相对中间点的方位向量,和特征分叉点相对中间点的方位向量。
对于一幅彻底细化的指纹图像来说,只有三种纹线点:(1)C n(P)=1,S n(P)=1,称为端点;(2)Cn(P)=2,Sn(P)=2,3,4,称为连续点;(3)C n(P)=3,S n(P)=3,
称为叉点。设提取的特征点集用 P(P1,P2,⋯,Pn )表示,其中 n 为所提取的特征37点的个数,Pi=(Xi ,Yi ,Ti,Ai),Xi,Yi 表示特征点的坐标;Ti 表示特征点的类型,当特征点为端点时 Ti=1,当特征点为端点时 Ti =2;a 表示特征点的角度,端点的角度取从端点为起点的端线的角度。端线及分支的角度求法为:从特征点开始搜索连续点直到搜到另一个特征点或步长达到 7,设搜索到的最后一点为(X,Y),有:
其对应的
Ti=sqrt((X-X0)^2+(Y-Y0)^2)
ai=(X-X0)/(Y-Y0)
(公式7-3)
9.4定义匹配点
PointOfModel(点集合 P 中的特征点)是从输入的指纹数字图像中提取出来的,另外一个匹配点 PointOfMatch(点集合 Q 中的特征点)则是从指纹数字图像库中提取出来储存在模板库中的,将两组点集合进行比对。
三、参考代码
代码1
[m,n]=size(f);
for j=n:-1:1
k=0;
for i=1:m
if(f(i,j)<=100)
k=1;
break;
end
end
if(k==0)
f(:,j)=[];
else
break
end
end
sizef=size(f);
for j=1:1:sizef(1,2)
k=0;
for i=1:m
if(f(i,j)<=100)
k=1;
break;
end
end
if(k~=0)
e=j;
break
end
end
f(:,1:e)=[];
sizef=size(f);
for i=sizef(1,1):-1:1
k=0;
for j=1:sizef(1,2)
if(f(i,j)<=100)
k=1;
break;
end
end
if(k==0)
f(i,:)=[];
else
break
end
end
sizef=size(f);
for i=1:1:sizef(1,1)
k=0;
for j=1:sizef(1,2)
if(f(i,j)<100)
k=1;
break;
end
end
if(k~=0)
e=i;
break
end
end
f(1:e,:)=[];
sizef=size(f);
modfx16=mod(sizef(1,1),32);
modfy16=mod(sizef(1,2),32);
for i=modfx16:-1:1
f(i,:)=[];
end
for j=modfy16:-1:1
f(:,j)=[];
end
代码2
function y=junheng(f)
sizef=size(f);
ff=f(:);
sizeff=size(ff);
unit=sizeff(1,1);
null1=ones(1,unit);
for i=1:unit-1
for j=i:unit
if(ff(i)<ff(j))
null1(j)=null1(j)+1;
elseif(ff(i)>ff(j))
null1(i)=null1(i)+1;
elseif((ff(i)==ff(j))&(ff(i)>150))
null1(j)=null1(j)+1;
null1(i)=null1(i)+1;
end
end
end
for i=1:unit
ff(i)=255*null1(i)/unit;
end
ff(8000:8010)
y=reshape(ff,sizef(1),sizef(2));
end
代码3
function y=guiyi(x,m)
sizef=size(x);
a=sizef(1,1);
b=sizef(1,2);
x1=double(x);
a1=a/m;
b1=b/m;
M0=mean2(x1);
V=std2(x1);
V0=V*V;
M1=M0*0,6;
V1=V0-2;
T=50;
a3=1;
b3=1;
for i=1:a
for j=1:b
if x1(i,j)>M0
result(i,j)=M1+sqrt(V1*((x1(i,j)-M0)*(x1(i,j)-M0))/V0);
else
result(i,j)=M1-sqrt(V1*((x1(i,j)-M0)*(x1(i,j)-M0))/V0);
end
end
end
for k=1:a1
for l=1:b1
M2=mean2(result(a3:(a3+m-1),b3:(b3+m-1)));
V2=std2(result(a3:(a3+m-1),b3:(b3+m-1)));
V3=V2*V2;
if V3<1000
for i1=a3:a3+m-1
for j1=b3:b3+m-1
result(i1,j1)=255;
end
end
end
if V2==0
for i1=a3:a3+m-1
for j1=b3:b3+m-1
result(i1,j1)=255;
end
end
else
Th=M2/V2;
if Th>T
for i1=a3:a3+m-1
for j1=b3:b3+m-1
result(i1,j1)=255;
end
end
end
end
b3=b3+m;
end
b3=1;
a3=a3+m;
end
代码4
function f= erzhi(f )
sizef=size(f);
cell1=sizef(1,1)/8;
cell2=sizef(1,2)/8;
f=double(f);
cell16=mat2cell(f,ones(sizef(1,1)/cell1,1)*cell1,ones(sizef(1,2)/cell2,1)*cell2);%8x8
fff=cell16;
for i=1:8
for j=1:8
fff{i,j}=fff{i,j}(:);
end
end
sum=zeros(8,8);
for i=1:8
for j=1:8
for m=1:cell1*cell2
sum(i,j)=sum(i,j)+fff{i,j}(m);
end
end
end
ave=sum/(cell1*cell2);
for i=1:8
for j=1:8
for m=1:cell1*cell2
if(fff{i,j}(m)<ave(i,j))
fff{i,j}(m)=0;
else
fff{i,j}(m)=1;
end
end
end
end
for i=1:8
for j=1:8
fff{i,j}=reshape(fff{i,j},cell1,cell2);
end
end
f=cell2mat(fff);
end
代码5
function f = xihua(f)
x=f;
I=ordfilt2(x,5,ones(3,3));
t=graythresh(I);
u=im2bw(I,t);
[m,n]=size(u);
for i=1:m
u(i,1)=1;
u(i,n)=1;
end
for j=1:n
u(1,j)=1;
u(m,j)=1;
end
for x=2:m-1
for y=2:n-1
if u(x,y)==0
if u(x,y-1)+u(x,y+1)+u(x+1,y)+u(x-1,y)>=3
u(x,y)=1;
else u(x,y)=u(x,y);
end
end
end
end
for a=2:m-1
for b=2:n-1
if u(a,b)==1
if abs(u(a,b+1)-u(a-1,b+1))+abs(u(a-1,b+1)-u(a-1,b))+abs(u(a-1,b)-u(a-1,b-1))+abs(u(a-1,b-1)-u(a,b-1))+abs(u(a,b-1)-u(a+1,b-1))+abs(u(a+1,b-1)-u(a+1,b))+abs(u(a+1,b)-u(a+1,b+1))+abs(u(a+1,b+1)-u(a,b+1))==1;
end
end
end
end
v=~u;
v=bwmorph(v,'hbreak',Inf);
w=bwmorph(v,'thin',Inf);
for x=2:m-1
for y=2:n-1
if w(x,y)==1
if(w(x-1,y)==1&w(x,y-1)==1)|(w(x-1,y)==1&w(x,y+1)==1)|(w(x,y-1)==1&w(x+1,y)==1)|(w(x+1,y)==1&w(x,y+1)==1);
w(x,y)=0;
end
end
end
end
f=~w;
[sizef1,sizef2]=size(f);
for i=2:1:sizef1-1
for j=2:1:sizef2-1
if (f(i,j)==0)
if(f(i-1,j)==0&f(i,j+1)==0)|(f(i-1,j)==0&f(i,j-1)==0)|(f(i+1,j)==0&f(i,j-1)==0)|(f(i,j+1)==0&f(i+1,j)==0)
f(i,j)=1;
else
f(i,j)=0;
end
end
end
end
end
代码6
function [x,y]= tezhengdian( f,h,l )
t=1;
h,l
for i=(h-55):(h+60)
for j=(l-80):(l+60)
if (abs(f(i-1,j+1)-f(i,j+1))+abs(f(i-1,j)-f(i-1,j+1))+abs(f(i-1,j-1)-f(i-1,j))+abs(f(i,j-1)-f(i-1,j-1))+abs(f(i+1,j-1)-f(i,j-1))+abs(f(i+1,j)-f(i+1,j-1))+abs(f(i+1,j+1)-f(i+1,j))+abs(f(i,j+1)-f(i+1,j+1))==6)&(f(i-1,j+1)+f(i,j+1)+f(i-1,j)+f(i-1,j-1)+f(i,j-1)+f(i+1,j-1)+f(i+1,j)+f(i+1,j+1)==5)
m(t)=i;
n(t)=j;
t=t+1;
end
end
end
t=t-1;
if t>115
for i=t-2:-1:2
for j=i-1:-1:1
d=sqrt((m(i)-m(j))^2+(n(i)-n(j))^2);
if d<2
m(i)=[];
n(i)=[];
end
end
end
x=m;
y=n;
end
end
代码7
function k=pipei( )
[r1,tan1]=jisuan(imread('D:\MATLAB2013a\bin\DB1_B\110_4.tif'));
[r2,tan2]=jisuan(imread('D:\MATLAB2013a\bin\DB1_B\110_4.tif'));
sizer1=size(r1);
sizer2=size(r2);
size1=sizer1(1,2);
sizemin=sizer2(1,2);
if(size1<sizemin)
sizemin=size1;
end
k=0;
m=2;
n=0.3;
for i=1:sizemin
for j=1:sizemin
if abs((r1(i)-r2(j)))<m
if(abs(tan1(i)-tan2(j))<n)
k=k+1;
end
end
end
end
end