本教程展示了如何使用各种图像处理命令来比较两个图像,以确定它们在使用LEADTOOLS SDK的c# Windows控制台应用程序中的相似程度。
| 概述 | |
|---|---|
| 总结 | 本教程介绍如何在c# Windows控制台应用程序中使用各种图像处理命令来比较图像。 |
| 完成时间 | 45分钟 |
| Visual Studio项目 | 下载教程项目(5kb) |
| 平台 | c# Windows控制台应用程序 |
| IDE | Visual Studio 2017, 2019 |
| 开发许可 | 下载LEADTOOLS |
| 用另一种语言试试 |
|
步骤熟悉创建项目的基本步骤添加引用和设置License教程,在工作之前比较图像数据的相似性-控制台c#教程。
中创建的项目的副本开始添加引用和设置License教程。如果您没有该项目,请按照该教程中的步骤创建它。
所需要的参考资料取决于项目的目的。引用可以通过以下两种方法中的一种添加(但不能同时添加)。
如果使用NuGet引用,本教程需要以下NuGet包:
Leadtools.Image.Processing如果使用本地DLL引用,则需要以下DLL。
dll位于< INSTALL_DIR > \ LEADTOOLS22 \ Bin \ Dotnet4 \ x64:
Leadtools.dllLeadtools.Codecs.dllLeadtools.Codecs.Cmp.dllLeadtools.Codecs.Png.dllLeadtools.ImageProcessing.Color.dllLeadtools.ImageProcessing.Core.dllLeadtools.ImageProcessing.Effects.dll有关应用程序需要哪些DLL文件的完整列表,请参阅在你的申请中包含的文件.
许可证解锁项目所需的特性。它必须在调用任何工具箱函数之前设置。有关详细信息,包括针对不同平台的教程,请参阅设置运行时License.
有两种类型的运行时许可证:
请注意
中详细介绍了添加LEADTOOLS NuGet和本地引用以及设置许可添加引用和设置License教程。
随着项目的创建、引用的添加和许可的设置,编码就可以开始了。
方法后,通过计算黑色像素的比例来比较两幅图像CombineCommand与OperationXor标志的所有像素的平均强度StatisticsInformationCommand的平均色相和饱和度值ColorSeparateCommand,各色频幅值之差与的平均值FastFourierTransformCommand.
在解决方案资源管理器,打开Program.cs.将以下语句添加到顶部的using块中Program.cs:
使用系统;使用先;使用Leadtools;使用Leadtools.Codecs;使用Leadtools.ImageProcessing;使用Leadtools.ImageProcessing.Color;使用Leadtools.ImageProcessing.Core;使用Leadtools.ImageProcessing.Effects;
在主要方法添加两个新的字符串变量,并将它们设置为两个单独的图像文件路径,如下所示。为了本教程的目的,您可以下载测试图像在这里.例如,比较1 stred.png与2 ndred.png.
静态无效主要(字符串[]参数){字符串image1Filename =@" filepath to first image ";字符串image2Filename =@" filepath to second image ";SetLicense ();// RasterImages是IDisposable的,所以如果以后没有调用.Dispose(),它们必须在使用block中使用(RasterImage image1 = LoadImage(image1Filename))使用(RasterImage image2 = LoadImage(image2Filename)){控制台。WriteLine ($"图像1:{image1Filename}");控制台。WriteLine ($"Image 2: {image2Filename}\n");CompareXOR (image1 image2);CompareIntensities (image1 image2);CompareHSV (image1 image2);CompareFourier (image1 image2);}控制台。WriteLine (“按任意键退出…”);控制台。ReadKey (真正的);}
控件中添加一个新方法程序类命名LoadImage(字符串_filePath).在内部调用该方法两次使用的声明主要方法调用SetLicense方法,如上所示。将下面的代码添加到LoadImage方法将给定文件加载为RasterImage对象。
静态RasterImage LoadImage (字符串文件名){使用(RasterCodecs codecs =新RasterCodecs ())返回codecs.Load(文件名);}
属性中添加四个新方法程序类命名比较xor (RasterImage image1, RasterImage image2),比较强度(RasterImage image1, RasterImage image2),比较hsv (RasterImage image1, RasterImage image2),比较傅立叶(RasterImage image1, RasterImage image2).方法调用下面的所有四个方法LoadImage方法,在使用语句,如上所示。
添加下面的代码CompareXOR方法。在这种方法中,我们将使用CombineCommand.这将一个图像放在另一个图像上,在一个特定的位置和特定的矩形内。底层图像的像素受覆盖图像影响的方式取决于我们使用的标志。在本例中,我们将使用aLeadRect这是与底部图像相同的大小来使用整个图像。我们将使用OperationXor标志,该标志将对每个图像的上下像素集执行逐位异或操作。这将创建黑色像素,其中两个像素在两个图像的同一位置是相同的,其他地方都是白色的。为了计算两幅图像之间有多少相同,我们将只从黑色像素中创建一个区域,并将其与所有像素的总和进行比较。
私人静态无效比较xor (RasterImage image1, RasterImage image2){使用(RasterImage image2Copy = image2.Clone()){//将图像进行异或合并新CombineCommand (){DestinationRectangle =新LeadRect(0,0, image1.)宽度,image1.Height),Flags =组合mandflags。OperationXor,SourceImage = image1,SourcePoint =新LeadPoint (0, 0)} .Run (image2Copy);//计算黑色像素的百分比(其中XOR相同)image2Copy.AddColorToRegion (RasterColor。黑色,RasterRegionCombineMode.Set);双比率= (双)image2Copy. calculateregionarea () / (image2Copy. calculateregionarea。宽度* image2Copy.Height);控制台。WriteLine ($“单个像素:{100.0 *比例:0.00}%匹配”);}}
添加下面的代码CompareIntensities方法创建StatisticsInformationCommand,它允许您只在统计种群中包含某个范围或颜色的像素。我们将使用主通道中0-255的所有像素。我们将收集图像的平均值并将两者进行比较,将其缩放为0-1.00而不是0-255。这将给我们平均强度或亮度的差异。
我们还可以使用这个命令通过异或来获得这些图像的差异强度CombineCommand像以前一样。这将通过相同像素值与不同像素值的比值来计算。
私人静态无效比较强度(RasterImage image1, RasterImage image2){使用(RasterImage image1Gray = image1.Clone())使用(RasterImage image2Gray = image1.Clone()){//将两个图像转换为灰度GrayscaleCommand grayscale =新GrayscaleCommand (){BitsPerPixel = 8};grayscale.Run (image1Gray);grayscale.Run (image2Gray);//比较总体平均强度statisticinformationcommand statistics =新StatisticsInformationCommand (){Channel = RasterColorChannel。主人,End = 255,Start = 0};statistics.Run (image1Gray);双leftIntensity = statistics.Mean;statistics.Run (image2Gray);双rightIntensity = statistics.Mean;双相似度= 1.0 -(数学。Abs(leftIntensity - rightIntensity) / 255.0);控制台。WriteLine ($“整体图像强度:{100.0 *相似度:0.00}%匹配”);//检查差异的强度新CombineCommand (){DestinationRectangle =新LeadRect(0,0, image1Gray。宽度,image1Gray.Height),Flags =组合mandflags。OperationXor,SourceImage = image1Gray,SourcePoint =新LeadPoint (0, 0)} .Run (image2Gray);statistics.Run (image2Gray);相似度= 1.0 -(统计。Mean / 255.0);控制台。WriteLine ($“图像差异强度:{100.0 *相似度:0.00}%匹配”);}}
添加下面的代码CompareHSV方法将图像分离为色相,饱和度和值通道,而不是红色,绿色和蓝色。这将创建一个DestinationImage对象,其中有三个页面,每个频道一个页面。然后我们可以使用StatisticsInformationCommand通过在分离图像的每一页上运行它,再次找到两张图像的平均色相和饱和度。平均值本质上是图像的亮度,这不是很有用。然后我们可以比较平均色相和饱和度的差异,再次将其从0-255缩放到0-100。
私人静态无效比较hsv (RasterImage image1, RasterImage image2){colorseparatcommand colorSeparate =新ColorSeparateCommand (){类型= ColorSeparateCommandType。Hsv};statisticinformationcommand statistics =新StatisticsInformationCommand (){Channel = RasterColorChannel。主人,End = 255,Start = 0};//分离第一个图像,计算平均值colorSeparate.Run (image1);双image1Hue image1Saturation;使用(RasterImage image1Separated = colorSeparate.DestinationImage){image1Separated。Page = 1;statistics.Run (image1Separated);image1Hue = statistics.Mean;image1Separated。Page = 2;statistics.Run (image1Separated);image1Saturation = statistics.Mean;}//分离第二张图像,计算平均值colorSeparate.Run (image2);双image2Hue image2Saturation;使用(RasterImage image2Separated = colorSeparate.DestinationImage){image2Separated。Page = 1;statistics.Run (image2Separated);image2Hue = statistics.Mean;image2Separated。Page = 2;statistics.Run (image2Separated);image2Saturation = statistics.Mean;}//计算色相差//注意:0在255后面,所以需要进行补偿双hueDiff =数学。Abs(image1Hue - image2Hue);如果(hueDiff > 127)hueDiff =数学。Abs(hueDiff - 255);//记录色调相似度双相似度= 1.0 - (hueDiff / 255.0);控制台。WriteLine ($"平均色相值:{100.0 *相似度:0.00}%匹配");//记录饱和度相似度相似度= 1.0 -(数学。Abs(image1Saturation - image2Saturation) / 255);控制台。WriteLine ($平均饱和度值:{100.0 *相似度:0.00}%匹配);}
最后,添加下面的代码CompareHSV方法比较两幅图像的频率分布FastFourierTransformCommand.快速傅里叶变换(FFT)的工作原理是将图像从空间域转换到频域,这对于滤除噪声等事情很有用。我们将用它来比较每个频率的幅度。运行命令之后,就可以使用info对象的命令了数据属性来获取复杂的与每个频率相关的数字,计算每个频率的幅度,并计算两个平均值之间的差值。
私人静态无效比较傅立叶(RasterImage image1, RasterImage image2){使用(RasterImage image1Copy = image1.Clone())使用(RasterImage image2Copy = image2.Clone()){//确保图像大小相同如果(image1Copy。宽度!= image2Copy。宽度|| image1Copy。= image2Copy.Height){//可以使用最小大小,但我们将它设置为固定的256 * 256size =新SizeCommand (){Flags = RasterSizeFlags。双三次的,高度= 256,宽度= 256};size.Run (image1Copy);size.Run (image2Copy);}//设置快速傅里叶变换数据//注意:我们需要padding标志,这样就可以处理非幂的大小FastFourierTransformCommandFlags = FastFourierTransformCommandFlags。FastFourierTransform| FastFourierTransformCommandFlags。灰色| FastFourierTransformCommandFlags.PadOptimally;FourierTransformInformation image1Info =新FourierTransformInformation (image1Copy fftFlags);FourierTransformInformation image2Info =新FourierTransformInformation (image2Copy fftFlags);//对两个图像应用FFTFastFourierTransformCommand fft =新FastFourierTransformCommand (){Flags = fftFlags,FourierTransformInformation = image1Info};fft.Run (image1Copy);fft。FourierTransformInformation = image2Info;fft.Run (image2Copy);//根据每个分量的大小计算频率的相似度双magnitudeTotal = 0;双magnitudeTotalDiff = 0;intlength = image1Info.Data.Length;Complex[] image1Data = image1Info.Data;Complex[] image2Data = image2Info.Data;为(intI = 0;I < length;我+ +){//计算每个条目的大小复杂image1Entry = image1Data[i];双image1Magnitude = Math.Sqrt(image1Entry. sqrt)R * image1Entry。R + image1Entry。I * image1entry I);复杂image2Entry = image2Data[i];双image2Magnitude = Math.Sqrt(image2Entry. sqrt)R * image2Entry。R + image2Entry。I * image2entry I);//加上总数magnitudeTotal += image1大小+ image2大小;magnitudeTotalDiff +=数学。Abs(image1Magnitude - image2Magnitude);}//确保不除以零如果(magnitudeTotal == 0)magnitudeTotal = 1;//记录结果双similarity = (magnitudeTotal - magnitudeTotalDiff) / magnitudeTotal;控制台。WriteLine ($频率比较:{100.0 *相似度:0.00}%匹配);}}
使用MemoryStream使用本教程,替换Main ()方法如下:
静态无效主要(字符串[]参数){字符串image1Filename =@" filepath to first image ";字符串image2Filename =@" filepath to second image ";试一试{SetLicense ();Console.WriteLine ();//使用内存流使用(RasterCodecs =新RasterCodecs ()){// RasterImages是IDisposable的,所以如果以后没有调用.Dispose(),它们必须在使用block中字节[] bytes1 = File.ReadAllBytes(image1Filename);字节[] bytes2 = File.ReadAllBytes(image2Filename);memoryStream1 =新MemoryStream (bytes1);memoryStream2 =新MemoryStream (bytes2);使用(RasterImage image1 = rasterCodecs.Load(memoryStream1))使用(RasterImage image2 = rasterCodecs.Load(memoryStream2)){控制台。WriteLine ($"图像1:{image1}");控制台。WriteLine ($"图片2:{image2}");Console.WriteLine ();CompareXOR (image1 image2);CompareIntensities (image1 image2);CompareHSV (image1 image2);CompareFourier (image1 image2);}}}抓(异常交货){Console.WriteLine (ex.Message);Console.WriteLine (ex.StackTrace);}Console.WriteLine ();控制台。WriteLine (“按任意键退出…”);控制台。ReadKey (真正的);}
按下运行项目F5,或选择Debug ->开始调试.
如果正确地执行了这些步骤,应用程序将运行并对两个图像执行多个计算,并将相似性统计信息输出到控制台。
本教程展示了如何使用各种图像处理命令,包括CombineCommand,GrayscaleCommand,StatisticsInformationCommand,ColorSeparateCommand,SizeCommand,FastFourierTransformCommand,得到两幅图像的相似度统计量。