65.9K
CodeProject 正在变化。 阅读更多。
Home

一个用于指纹识别的 C# 框架

starIconstarIconstarIconstarIcon
emptyStarIcon
starIcon

4.95/5 (279投票s)

2010 年 7 月 30 日

CPOL

11分钟阅读

viewsIcon

1790226

downloadIcon

143954

在本文中,我们介绍了一个用于指纹验证的 C# 框架,简要说明了如何执行指纹验证实验以及如何将您的算法集成到框架中。

引言

指纹识别 [1] 是当今一个活跃的研究领域。指纹识别系统中一个重要的组成部分是指纹匹配算法。根据问题域,指纹匹配算法被分为两类:指纹验证算法和指纹识别算法。指纹验证算法的目的是确定两个指纹是否来自同一手指。另一方面,指纹识别算法在一个数据库中搜索一个查询指纹,以查找来自同一手指的指纹。

关于指纹验证的论文有数百篇,但据我们所知,网上并没有现成的指纹验证框架。因此,您必须实现自己的工具来测试指纹验证算法的性能。此外,您必须花费大量时间来实现其他作者的算法以与您的算法进行比较。这就是我们推出指纹验证框架供大家使用的动机。

与我们的框架最相关的项目是 FVC-onGoing 网页系统。该系统存在以下局限性:

  • 除了您自己的算法外,您无法访问任何其他算法。
  • 它不是一个框架,因此您无法重用任何软件组件。
  • 它不能用于教育目的,因为学生无法看到算法的工作原理。
  • 在使用数据库(标准或困难)执行实验后,您必须等待 30 天才能使用相同的数据库执行另一个实验。
  • 您无法控制指纹数据库。因此,您不能使用自己的数据库,也不能修改现有数据库。
  • 您无法访问您的算法匹配失败的指纹。因此,您无法分析算法为何失败以便修复您的代码。
  • 您无法创建一个具有自定义协议以进行性能评估的实验。

如果上述任何限制对您造成了问题,那么您应该使用我们的框架。

我们的框架采用 C# 和 .NET Framework 实现,主要有两个原因。首先,C# 已成为最受欢迎的编程语言之一。其次,.NET Framework 中提供的技术、工具和类库为我们节省了大量的编码时间。

我们的框架允许对 FVC2000、FVC2002 和 FVC2004 的 B 数据库以及 FVC2002 和 FVC2004 的 A 数据库进行指纹验证实验。在这些实验中,我们使用了指纹验证竞赛 [2] 的性能指标(EER(%)、FMR100(%)、FMR1000(%)、ZeroFMR(%)、Time(ms) 和 ROC 曲线)。此外,您可以包含具有自定义评估协议或不同数据库的实验。

我们实现了 Tico 和 Kuosmanen [3]、Jiang 和 Yau [4]、Medina-Pérez 等人 [5, 6, 8, 12] 以及 Qi 等人 [9] 提出的指纹验证算法。需要强调的是,尽管 Qi 等人的算法是细节匹配算法与基于方向的算法的组合,但我们只实现了细节匹配算法。我们还实现了 Ratha 等人 [10] 提出的特征提取算法以及 Sherlock 等人 [11] 提出的方向图像提取器。该框架允许您以最小的精力添加新的指纹匹配算法以及新的特征提取算法,而无需重新编译框架。

我们在开发此框架时牢记的目标之一是实现尽可能简单的类接口。这样,添加新算法就非常直接。

我们希望这项工作能激励您和更多人与我们合作,以实现更多算法。

在本文中,我们简要说明了如何

  • 执行指纹验证实验,
  • 查看使用基于细节的算法执行实验后匹配的细节,
  • 计算并显示特定指纹的特征,
  • 将您的算法集成到框架中。

使用框架之前

此框架的一个仅用于研究目的的扩展版本出现在 https://sites.google.com/site/miguelmedinaperez/software/fprframework

在本文中,我们提供了以下文件:

您可以实现自定义评估协议,也可以使用自己的数据库。尽管如此,我们还是实现了用于处理以下数据库的评估协议:

运行指纹验证实验

解压“FingerprintRecognition.zip”文件并生成解决方案。然后您可以调试“FR.FVCExperimenter”项目,或者在包含生成程序集的目录中执行“FR.FVCExperimenter.exe”。将打开以下窗口:

在“Resources”文本框中,指定要使用的数据库的路径,例如:“D:\PR Databases\Fingerprints\FVC2004\DB1_B”。在带有“Experiment”标签的组合框中选择合适的实验类型。使用“Minutia Extractor”、“Orientation Image Extractor”和“Skeleton Image Extractor”组合框来选择用于计算基本特征(细节、方向图像和骨架图像)的算法。

使用带有“Matcher”标签的组合框选择一个指纹验证算法,并使用带有“Feature Provider”标签的组合框选择将用于为所选匹配器存储和检索特征的算法。尽管我们为每个匹配器实现了一个特征提供者,但存在您可能为每个匹配器拥有多个特征提供者的情况。

带有“Properties”标签的网格允许更改任何选定算法的参数。

点击“Execute Experiment”按钮运行实验。此实验使用指纹验证竞赛 [2] 的评估协议。在此实验中计算的性能指标是:EER(%)、FMR100(%)、FMR1000(%)、ZeroFMR(%)、Time(ms) 和 ROC 曲线。这些指标保存在一个文件中,该文件的名称由匹配算法的名称加上“.Summary.csv”组成。该文件保存在指纹存储位置同一文件夹下的“Results”文件夹中。还会保存另外两个文件,一个文件包含错误匹配的指纹,另一个文件包含错误不匹配的指纹。

如果您想匹配两个指纹并验证重合的细节,请单击“Visual Match”按钮,这将打开“Visual Fingerprint Matching”窗体。加载要比较的指纹,然后单击“Match”按钮。“FVC Experimenter”中选择的特征提取器和匹配器也用于在此处执行指纹匹配。下面是匹配两个指纹的示例:

可视化特征

如果您想可视化特定指纹的特征,您可以使用“FR.FeatureDisplay”项目。在“Fingerprint Feature Display”窗体中,您可以更改特征提取器和特征显示。在框架中,我们包含了可视化细节、方向图像和骨架图像的类。

下面是一个可视化指纹方向图像的示例:

在框架外匹配指纹

本节将举例说明如何使用框架在自定义用户应用程序中匹配两个指纹图像。它包括比较两个指纹图像的三个步骤:图像加载、特征提取和特征比较。在这种情况下,用户需要从他们的应用程序添加对程序集 FR.Core 和 FR.Medina2012 的引用。程序集 SHullDelaunayTriangulationImageProcessingTools 必须包含在二进制文件出现的输出文件夹中。

// Loading fingerprints
var fingerprintImg1 = ImageLoader.LoadImage(fileName1);
var fingerprintImg2 = ImageLoader.LoadImage(fileName2);

// Building feature extractor and extracting features
var featExtractor = new MTripletsExtractor(){ MtiaExtractor = new Ratha1995MinutiaeExtractor()};
var features1  =  featExtractor.ExtractFeatures(fingerprintImg1);
var features2  =  featExtractor.ExtractFeatures(fingerprintImg2);

// Building matcher and matching
var matcher = new M3gl();
double similarity = matcher.Match(features1, features2); 

使用 M3gl 匹配器的示例展示了使用框架的简便性,以及用户代码的简洁和自解释性。框架中应用的良好设计规则允许用户以最小的精力替换或更改任何组件。例如,要在上述代码中使用 PN 匹配器,用户只需将 MTripletsExtractor 替换为 PNFeatureExtractor,将 M3gl 替换为 PN,并将 FR.Medina2012 的引用替换为 FR.Parziale2004

向框架添加新算法

您需要知道的第一件事是,您无需修改框架的应用程序即可识别您的算法,因为我们使用反射在执行时动态加载所有算法。

您可以在包含框架的目录中创建任意数量的程序集。对于每个新程序集,转到属性并设置输出路径为“..\bin\Release\”。

为了添加新的特征提取器,您必须继承泛型类 FeatureExtractor<T> 并实现方法 ExtractFeatures(Bitmap image)。例如,假设您想创建一个类型为 MyFeature 的特征提取器,您可以实现一个如下所示的类:

public class MyFeatureExtractor : FeatureExtractor<MyFeature>
{
    public override MyFeature ExtractFeatures(Bitmap image)
    {
        // Place here your code to extract features
    }
} 

如果您的新特征建立在某些现有特征的基础上,您可以这样做:

public class MyFeatureExtractor : FeatureExtractor<MyFeature>
{     
    public FeatureExtractor<List<Minutia>> MtiaExtractor { set; get; }

    public FeatureExtractor<OrientationImage> OrImgExtractor { set; get; }

    public override MyFeature ExtractFeatures(Bitmap image)
    {
    try
        {
             var mtiae = MtiaExtractor.ExtractFeatures(image);
             var orImg = OrImgExtractor.ExtractFeatures(image);
             return ExtractFeatures(mtiae, orImg);
        }
        catch (Exception e)
        {
             if (MtiaExtractor == null)
                throw new InvalidOperationException("Cannot extract MyFeature: 
                                               Unassigned minutia list extractor!", e);
             if (OrImgExtractor == null)
                throw new InvalidOperationException("Cannot extract MyFeature: 
                                               Unassigned orientation image extractor!", e);
             throw;
        }
    }

    public MyFeature ExtractFeatures(List<Minutia> mtiae, OrientationImage orImg)
    {
        // Place here your code to extract features
    }       
}

对于每个特征提取器,您必须创建一个资源提供者。资源提供者允许将与指纹相关的资源保存到(从)文件。框架包含用于细节(MinutiaListProvider)、方向图像(OrientationImageProvider)和骨架图像(SkeletonImageProvider)提取器的资源提供者。下面是一个上面定义的特征提取器的资源提供者的示例。

public class MyFeatureProvider : ResourceProvider<MyFeature>
{
    public MinutiaListProvider MtiaListProvider { get; set; }

    public OrientationImageProvider OrImgProvider { get; set; }

    public override string GetSignature()
    {
        return "myf";        
    }

    public override bool IsResourcePersistent()
    {
        return true;
    }

    protected override MyFeature Extract(string fingerprint, ResourceRepository repository)
    {
        try
        {
            var mtiae = MtiaListProvider.GetResource(fingerprint, repository);
            var orImg = OrImgProvider.GetResource(fingerprint, repository);
            return featureExtractor.ExtractFeatures(mtiae, orImg);
        }
        catch (Exception e)
        {
            if (MtiaListProvider == null)
                throw new InvalidOperationException
                     ("Unable to extract MyFeature: Unassigned minutia list provider!", e);
            if (OrImgProvider == null)
                throw new InvalidOperationException
                     ("Unable to extract MyFeature: Unassigned orientation image provider!", e);
            throw;
        }
    }

    private MyFeatureExtractor featureExtractor = new MyFeatureExtractor();
}

现在,是时候创建一个新的指纹匹配算法了。假设您想匹配类型为 MyFeature 的特征,那么您必须创建一个如下所示的匹配器:

public class MyMatcher : Matcher<MyFeature>
{        
    public override double Match(MyFeature query, MyFeature template)
    {
        // Place here your code to match fingerprints
    }
}

如果您正在实现一个细节匹配算法,那么您应该修改上面的代码如下:

public class MyMatcher : Matcher<MyFeature>, IMinutiaMatcher
{
    public override double Match(MyFeature query, MyFeature template)
    {
        List<MinutiaPair> matchingMtiae;
        return Match(query, template, out matchingMtiae);
    }

    public double Match(object query, object template, out List<MinutiaPair> matchingMtiae)
    {
        // Place here your code to match fingerprints
    }
}

将现有算法集成到框架中

用户无需修改框架即可集成自定义算法,因为使用反射在执行时动态加载所有算法。这样,用户应该将新算法添加到他们自己的自定义程序集中。

为了在框架中使用现有的匹配算法,用户首先需要做的是创建一个资源提供者。资源提供者允许将与指纹相关的资源保存到(从)文件中。例如,假设用户想将 SourceAFIS SDK(http://www.sourceafis.org/)集成到框架中,那么可以使用以下特征提供者:

public class SourceAFISFeatureProvider : ResourceProvider<Person>
{
  protected  override  Person  Extract(string  fingerprint, ResourceRepository repository)
  {
    Fingerprint fp = new  Fingerprint();
    fp.AsBitmap = imageProvider.GetResource(fingerprint, repository); 
    Person person = new Person(); 
    person.Fingerprints.Add(fp); 
    Afis.Extract(person);
    return person;
  }

  public override string GetSignature()
  {
    return string.Format("sAFIS");
  }

  public  override  bool  IsResourcePersistent()
  {
    return true;
  }
  
  private static AfisEngine Afis = new AfisEngine();
} 

现在,指纹匹配算法可以包装在以下类中:

public class SourceAFISMatcher : Matcher<Person>
{
  public override double Match(Person query, Person template)
  {
    return Afis.Verify(query, template);
  }
  
  private static AfisEngine Afis = new AfisEngine();
} 

实验结果

我们对本框架中包含的指纹匹配算法进行了广泛的实验。实验设置以及结果的统计分析可以在 [13] 中查阅。

结论

在本文中,我们介绍了 C# 指纹验证框架。我们简要说明了如何执行指纹验证实验以及如何将您的算法集成到框架中。我们提供了几种匹配算法和特征提取算法,您不仅可以用于实验目的,还可以用于创建您自己的应用程序。我们提供了所有算法的源代码,因此用户可以重用代码的任何部分以及任何软件组件。

致谢

我们感谢 MSc. Dania Yudith Suárez Abreu 在改进本文语法和风格方面做出的贡献。感谢 Jani Giannoudis 建议在示例中包含内部异常参数。

参考文献

  1. D. Maltoni, D. Maio, A. K. Jain, and S. Prabhakar, "Handbook of fingerprint recognition," Second ed. London: Springer-Verlag, 2009.
  2. R. Cappelli, D. Maio, D. Maltoni, J. L. Wayman, and A. K. Jain, "Performance evaluation of fingerprint verification systems," IEEE Transactions on Pattern Analysis and Machine Intelligence, vol. 28, pp. 3-18, 2006.
  3. M. Tico and P. Kuosmanen, "Fingerprint matching using an orientation-based minutia descriptor," IEEE Transactions on Pattern Analysis and Machine Intelligence, vol. 25, pp. 1009-1014, 2003.
  4. X. Jiang and W. Y. Yau, "Fingerprint minutiae matching based on the local and global structures," in 15th International Conference on Pattern Recognition, Barcelona, Spain, 2000, pp. 1038-1041.
  5. M. A. Medina-Pérez, A. Gutiérrez-Rodríguez, and M. García-Borroto, "Improving fingerprint matching using an orientation-based minutia descriptor," in 14th Iberoamerican Congress on Pattern Recognition, CIARP 2009, Guadalajara, México, 2009, pp. 121-128.
  6. M. A. Medina-Pérez, M. García-Borroto, A. E. Gutierrez-Rodriguez, L. Altamirano-Robles, "Robust fingerprint verification using m-triplets," in: International Conference on Hand-Based Biometrics (ICHB 2011), Hong Kong, 2011, pp. 1-5. (DOI: 10.1109/ICHB.2011.6094348. E-ISBN: 978-1-4577-0489-5. Print ISBN: 978-1-4577-0491-8).
  7. W. Wang, J. Li, and W. Chen, "Fingerprint minutiae matching based on coordinate system bank and global optimum alignment," in 18th International Conference on Pattern Recognition, 2006, vol. 4, pp. 401-404.
  8. M. A. Medina-Pérez, M. García-Borroto, A. E. Gutierrez-Rodriguez, L. Altamirano-Robles, "Improving the multiple alignments strategy for fingerprint verification," Lecture Notes in Computer Science, vol. 7329, 2012. (Accepted for publication)
  9. J. Qi, S. Yang, and Y. Wang, "Fingerprint matching combining the global orientation field with minutia," Pattern Recognition Letters, vol. 26, pp. 2424-2430, 2005.
  10. N. Ratha, S. Chen, and A. K. Jain, "Adaptive flow orientation-based feature extraction in fingerprint images," Pattern Recognition, vol. 28, pp. 1657-1672, 1995.
  11. B. G. Sherlock, D. M. Monro, and K. Millard, "Fingerprint enhancement by directional Fourier filtering," IEE Proceedings Vision Image and Signal Processing, vol. 141, no. 2, pp. 87-94, 1994.
  12. M. A. Medina-Pérez, M. García-Borroto, A. E. Gutierrez-Rodríguez, and L. Altamirano-Robles, “Improving Fingerprint Verification Using Minutiae Triplets,” Sensors, vol. 12, pp. 3418–3437, 2012.
  13. M. A. Medina-Pérez, O. Loyola-González, A. E. Gutierrez-Rodríguez, M. García-Borroto, and L. Altamirano-Robles, “Introducing an experimental framework in C # for fingerprint recognition,” Lecture Notes in Computer Science, vol. 8495, pp. 132–141, 2014.
© . All rights reserved.