c# 预处理识别硬币的数据集

在文章中,我们将对输入到机器学习模型中的数据集进行预处理。

这里我们将对一个硬币数据集进行预处理,以便以后在监督学习模型中进行训练。在机器学习中预处理数据集通常涉及以下任务:

  1. 清理数据——通过对周围数据的平均值或使用其他策略来填补数据缺失或损坏造成的漏洞。
  2. 规范数据——将数据缩放值标准化到一个标准范围,通常是0到1。具有广泛值范围的数据可能会导致不规范,因此我们将所有数据都放在一个公共范围内。
  3. 一种热编码标签——将数据集中对象的标签或类编码为N维二进制向量,其中N是类的总数。数组元素都被设置为0,除了与对象的类相对应的元素,它被设置为1。这意味着在每个数组中都有一个值为1的元素。
  4. 将输入数据集分为训练集和验证集——训练集被用于训练模型,验证集是用于检查我们的训练结果。

这个例子我们将使用Numpy.NET,它基本上是Python中流行的Numpy库的.NET版本。

Numpy是一个专注于处理矩阵的库。

为了实现我们的数据集处理器,我们在PreProcessing文件夹中创建Utils类和DataSet类。Utils类合并了一个静态Normalize 方法,如下所示:

public class Utils
  {
    public static NDarray Normalize(string path)
    {
      var colorMode = Settings.Channels == 3 ? "rgb" : "grayscale";
      var img = ImageUtil.LoadImg(path, color_mode: colorMode, target_size: (Settings.ImgWidth, Settings.ImgHeight));
      return ImageUtil.ImageToArray(img) / 255;
    }

  }

在这种方法中,我们用给定的颜色模式(RGB或灰度)加载图像,并将其调整为给定的宽度和高度。然后我们返回包含图像的矩阵,每个元素除以255。每个元素除以255是使它们标准化,因为图像中任何像素的值都在0到255之间,所以通过将它们除以255,我们确保了新的范围是0到1,包括255。

我们还在代码中使用了一个Settings类。该类包含用于跨应用程序使用的许多常量。另一个类DataSet,表示我们将要用来训练机器学习模型的数据集。这里我们有以下字段:

  1. _pathToFolder—包含图像的文件夹的路径。
  2. _extList—要考虑的文件扩展名列表。
  3. _labels—_pathToFolder中图像的标签或类。
  4. _objs -图像本身,表示为Numpy.NDarray。
  5. _validationSplit—用于将总图像数划分为验证集和训练集的百分比,在本例中,百分比将定义验证集与总图像数之间的大小。
  6. NumberClasses-数据集中唯一类的总数。
  7. TrainX -训练数据,表示为Numpy.NDarray。
  8. TrainY -训练标签,表示为Numpy.NDarray。
  9. ValidationX—验证数据,表示为Numpy.NDarray。
  10. ValidationY-验证标签,表示为Numpy.NDarray。

这是DataSet类:

public class DataSet
  {
    private string _pathToFolder;
    private string[] _extList;
    private List<int> _labels;
    private List<NDarray> _objs;
    private double _validationSplit;
    public int NumberClasses { get; set; }
    public NDarray TrainX { get; set; }
    public NDarray ValidationX { get; set; }
    public NDarray TrainY { get; set; }
    public NDarray ValidationY { get; set; }

    public DataSet(string pathToFolder, string[] extList, int numberClasses, double validationSplit)
    {
      _pathToFolder = pathToFolder;
      _extList = extList;
      NumberClasses = numberClasses;
      _labels = new List<int>();
      _objs = new List<NDarray>();
      _validationSplit = validationSplit;
    }

    public void LoadDataSet()
    {
      // Process the list of files found in the directory.
      string[] fileEntries = Directory.GetFiles(_pathToFolder);
      foreach (string fileName in fileEntries)
        if (IsRequiredExtFile(fileName))
          ProcessFile(fileName);

      MapToClassRange();
      GetTrainValidationData();
    }

    private bool IsRequiredExtFile(string fileName)
    {
      foreach (var ext in _extList)
      {
        if (fileName.Contains("." + ext))
        {
          return true;
        }
      }

      return false;
    }

    private void MapToClassRange()
    {
      HashSet<int> uniqueLabels = _labels.ToHashSet();
      var uniqueLabelList = uniqueLabels.ToList();
      uniqueLabelList.Sort();

      _labels = _labels.Select(x => uniqueLabelList.IndexOf(x)).ToList();
    }

    private NDarray OneHotEncoding(List<int> labels)
    {
      var npLabels = np.array(labels.ToArray()).reshape(-1);
      return Util.ToCategorical(npLabels, num_classes: NumberClasses);
    }

    private void ProcessFile(string path)
    {
      _objs.Add(Utils.Normalize(path));
      ProcessLabel(Path.GetFileName(path));
    }

    private void ProcessLabel(string filename)
    {
      _labels.Add(int.Parse(ExtractClassFromFileName(filename)));
    }

    private string ExtractClassFromFileName(string filename)
    {
      return filename.Split('_')[0].Replace("class", "");
    }

    private void GetTrainValidationData()
    {
      var listIndices = Enumerable.Range(0, _labels.Count).ToList();
      var toValidate = _objs.Count * _validationSplit;
      var random = new Random();
      var xValResult = new List<NDarray>();
      var yValResult = new List<int>();
      var xTrainResult = new List<NDarray>();
      var yTrainResult = new List<int>();

      // Split validation data
      for (var i = 0; i < toValidate; i++)
      {
        var randomIndex = random.Next(0, listIndices.Count);
        var indexVal = listIndices[randomIndex];
        xValResult.Add(_objs[indexVal]);
        yValResult.Add(_labels[indexVal]);
        listIndices.RemoveAt(randomIndex);
      }

      // Split rest (training data)
      listIndices.ForEach(indexVal =>
      {
        xTrainResult.Add(_objs[indexVal]);
        yTrainResult.Add(_labels[indexVal]);
      });

      TrainY = OneHotEncoding(yTrainResult);
      ValidationY = OneHotEncoding(yValResult);
      TrainX = np.array(xTrainResult);
      ValidationX = np.array(xValResult);
    }
}

下面是每个方法的说明:

  1. LoadDataSet()——类的主方法,我们调用它来加载_pathToFolder中的数据集。它调用下面列出的其他方法来完成此操作。
  2. IsRequiredExtFile(filename) - 检查给定文件是否包含至少一个应该为该数据集处理的扩展名(在_extList中列出)。
  3. MapToClassRange() -获取数据集中唯一标签的列表。
  4. ProcessFile(path) -使用Utils.Normalize方法对图像进行规格化,并调用ProcessLabel方法。
  5. ProcessLabel(filename)——将ExtractClassFromFileName方法的结果添加为标签。
  6. ExtractClassFromFileName(filename) -从图像的文件名中提取类。
  7. GetTrainValidationData()——将数据集划分为训练子数据集和验证子数据集。

在本系列中,我们将使用https://cvl.tuwien.ac.at/research/cvl-databases/coin-image-dataset/上的硬币图像数据集。

要加载数据集,我们可以在控制台应用程序的主类中包含以下内容:

var numberClasses = 60;
var fileExt = new string[] { ".png" };
var dataSetFilePath = @"C:/Users/arnal/Downloads/coin_dataset";
var dataSet = new PreProcessing.DataSet(dataSetFilePath, fileExt, numberClasses, 0.2);
dataSet.LoadDataSet();

我们的数据现在可以输入到机器学习模型中。下一篇文章将介绍监督机器学习的基础知识,以及训练和验证阶段包括哪些内容。它是为没有AI经验的读者准备的。

以上就是c# 预处理识别硬币的数据集的详细内容,更多关于c# 识别数据集的资料请关注我们其它相关文章!

(0)

相关推荐

  • C#中的预处理器指令详解

    目录 1. #define 和 #undef 2. #if.#elif.#else 和#endif 3. #warning 和 #error 4. #region 和#endregion 5. #line 6. #pragma C#中有许多名为"预处理器指令"的命令.这些命令从来不会转化为可执行代码中的命令,但会影响编译过程的各个方面. 例如,使用预处理器指令可以禁止编译器编译代码的某一部分.如果计划发布两个版本的代码,即基本版本和拥有更多功能的企业版本,就可以使用这些预处理器指令.在

  • C#中遍历DataSet数据集对象实例

    本文介绍C#上如何使用DataSet对象,并对DataSet对象中的表进行遍历,同时遍历表中的每一行,遍历每一行的每一列的值. 首先什么是DataSet,在C#中,Dataset就像一个数据库,其中可以有多个表(Table),也可以只有一个表,每个表中有行(DataRow)和列(DataColumn).使用DataRow[DataColumn]的形式可以得到某行某列数据值. 复制代码 代码如下: //下面例子中使用foreach来遍历DataSet中的所有表,对于每个表遍历所有的记录,并输出每一

  • C#预处理器指令的用法实例分析

    本文实例讲述了C#预处理器指令的用法.分享给大家供大家参考.具体用法分析如下: C#预处理器指令是在编译时调用的.预处理器指令(preprocessor directive)告诉C#编译器要编译哪些代码,并指出如何处理特定的错误和警告.C#预处理器指令还可以告诉C#编辑器有关代码组织的信息. 1. 定义符号和取消符号定义的预处理指令#define 和 #undef 预处理指令都以#号开头并位于行首前面可以出现空格符. 复制代码 代码如下: #define DEBUG #define ISSAY

  • c# 使用OpenCV识别硬币

    在本系列文章中,我们将使用深度神经网络(DNN)来执行硬币识别.具体来说,我们将训练一个DNN识别图像中的硬币. 在本文中,我们将描述一个OpenCV应用程序,它将检测图像中的硬币.硬币检测是硬币完整识别之前的一个常见阶段.它包括从给定图像中检测和提取硬币. 本系列附带的代码将使用Keras在C#中实现.在本系列的最后一篇文章中,我们将简要地使用ML.NET.在众多选择中,为什么要使用Keras.NET呢?Keras.NET 非常容易学习,因为它基本上是从Python编写的经典TensorFlo

  • C#使用linq查询大数据集的方法

    本文实例讲述了C#使用linq查询大数据集的方法.分享给大家供大家参考.具体如下: using System; using System.Collections.Generic; using System.Linq; using System.Text; namespace LargeNumberQuery { class Program { static void Main(string[] args) { int[] numbers = CreateNumbers(7384738); Con

  • C#中变量、常量、枚举、预处理器指令知多少

    一.变量 C#共有其中变量类型有:静态变量.实类变量.数组元素.数值参数.引用参数.输出参数和局部变量 先定义一个简单的类来说明,如下: public class VariableDefine { private static uint variableUInt; public static uint VariableUInt { get => variableUInt; set => variableUInt = value; } string VariableStr; public Var

  • C#使用SQL Dataset数据集代码实例

    ADO.NET数据访问技术的一个突出特点就是支持离线访问,而实现这种离线访问的技术核心急速DataSet对象,该对象通过数据驻留在内存来实现离线访问. DataSet对象由一组DataTable对象组成,这些对象与DataRelation对象又包含Row(行),集合,Columns(列)集合,Rows集合是有多个DAtaRow对象组成,Columns集合是由多个Datacolumns对象组成. 步骤: 1,引入命名空间System.Data: 2,创建DataSet对象 3,创建DataTabl

  • C#使用TensorFlow.NET训练自己的数据集的方法

    今天,我结合代码来详细介绍如何使用 SciSharp STACK 的 TensorFlow.NET 来训练CNN模型,该模型主要实现 图像的分类 ,可以直接移植该代码在 CPU 或 GPU 下使用,并针对你们自己本地的图像数据集进行训练和推理.TensorFlow.NET是基于 .NET Standard 框架的完整实现的TensorFlow,可以支持 .NET Framework 或 .NET CORE , TensorFlow.NET 为广大.NET开发者提供了完美的机器学习框架选择. Sc

  • C#预处理指令之#line,#pragma warning 详细解析

    #line #line 使您可以修改编译器的行号以及(可选)错误和警告的文件名输出.下面的示例说明如何报告与行号关联的两个警告.#line 200 指令强迫行号为 200(尽管默认值为 #7).另一行 (#9) 作为默认 #line 指令的结果跟在通常序列后. 复制代码 代码如下: class MainClass{     static void Main()      {         #line 200         int i; // CS0168 on line 200       

  • c#预处理指令分析

    预处理指令 这些指令/命令不会转换为可执行代码,但会影响编译过程的各个方面:列如,可以让编译器不编译某一部分代码等. C#中主要的预处理指令 #define和#undef #define指令定义: #define DEBUG 它告诉编译器存在DEBUG这个符号:这个符号不是实际代码的一部分,而只是在编译器编译代码时候可能会根据这个符号做条件编译. #undef定义: #undef DEBUG 用来移除定义的符号DEBUG.如果不存在这样的标记,#undef指令则不会生效.同样,用#define再

随机推荐