C# OpenCvSharp DNN FreeYOLO 人脸检测人脸图像质量评估

本文主要是介绍C# OpenCvSharp DNN FreeYOLO 人脸检测人脸图像质量评估,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

目录

效果

模型信息

yolo_free_huge_widerface_192x320.onnx

face-quality-assessment.onnx

项目

代码

frmMain.cs

FreeYoloFace

FaceQualityAssessment.cs

下载


C# OpenCvSharp DNN FreeYOLO 人脸检测&人脸图像质量评估

效果

模型信息

yolo_free_huge_widerface_192x320.onnx


Inputs
-------------------------
name:input
tensor:Float[1, 3, 192, 320]
---------------------------------------------------------------

Outputs
-------------------------
name:output
tensor:Float[1, 1260, 6]
---------------------------------------------------------------

face-quality-assessment.onnx

Inputs
-------------------------
name:input
tensor:Float[1, 3, 112, 112]
---------------------------------------------------------------

Outputs
-------------------------
name:quality
tensor:Float[1, 10]
---------------------------------------------------------------

项目

代码

frmMain.cs

using OpenCvSharp;
using System;
using System.Collections.Generic;
using System.Drawing;
using System.Text;
using System.Windows.Forms;

namespace OpenCvSharp_DNN_Demo
{
    public partial class frmMain : Form
    {
        public frmMain()
        {
            InitializeComponent();
        }

        string fileFilter = "*.*|*.bmp;*.jpg;*.jpeg;*.tiff;*.tiff;*.png";
        string image_path = "";

        DateTime dt1 = DateTime.Now;
        DateTime dt2 = DateTime.Now;

        StringBuilder sb = new StringBuilder();

        Mat image;
        Mat result_image;

        FaceQualityAssessment fqa = new FaceQualityAssessment("model/face-quality-assessment.onnx");
        FreeYoloFace face = new FreeYoloFace("model/yolo_free_huge_widerface_192x320.onnx");

        private void button1_Click(object sender, EventArgs e)
        {
            OpenFileDialog ofd = new OpenFileDialog();
            ofd.Filter = fileFilter;
            if (ofd.ShowDialog() != DialogResult.OK) return;

            pictureBox1.Image = null;
            pictureBox2.Image = null;
            textBox1.Text = "";

            image_path = ofd.FileName;
            pictureBox1.Image = new Bitmap(image_path);
            image = new Mat(image_path);
        }

        private void Form1_Load(object sender, EventArgs e)
        {
            image_path = "test_img/1.jpg";
            pictureBox1.Image = new Bitmap(image_path);
        }

        private unsafe void button2_Click(object sender, EventArgs e)
        {
            if (image_path == "")
            {
                return;
            }
            textBox1.Text = "检测中,请稍等……";
            if (pictureBox2.Image != null)
            {
                pictureBox2.Image.Dispose();
            }
            pictureBox2.Image = null;
            sb.Clear();
            Application.DoEvents();

            image = new Mat(image_path);

            dt1 = DateTime.Now;
            List<Face> ltFace = face.Detect(image);
            dt2 = DateTime.Now;

            if (ltFace.Count > 0)
            {
                sb.AppendLine("推理耗时:" + (dt2 - dt1).TotalMilliseconds + "ms");
                result_image = image.Clone();
                foreach (var item in ltFace)
                {
                    Mat crop_img = new Mat(image, item.rect);
                    float fqa_prob_mean = fqa.Detect(crop_img);
                    crop_img.Dispose();
                    Cv2.Rectangle(result_image, new OpenCvSharp.Point(item.rect.X, item.rect.Y), new OpenCvSharp.Point(item.rect.X + item.rect.Width, item.rect.Y + item.rect.Height), new Scalar(0, 0, 255), 2);
                    string label = "prob:" + item.prob.ToString("0.00") + " fqa_score:" + fqa_prob_mean.ToString("0.00");
                    sb.AppendLine(label);
                    Cv2.PutText(result_image, label, new OpenCvSharp.Point(item.rect.X, item.rect.Y - 5), HersheyFonts.HersheySimplex, 1, new Scalar(0, 0, 255), 2);
                }
                pictureBox2.Image = new Bitmap(result_image.ToMemoryStream());
                textBox1.Text = sb.ToString();
            }
            else
            {
                textBox1.Text = "未检测到人脸";
            }
        }

        private void pictureBox2_DoubleClick(object sender, EventArgs e)
        {
            Common.ShowNormalImg(pictureBox2.Image);
        }

        private void pictureBox1_DoubleClick(object sender, EventArgs e)
        {
            Common.ShowNormalImg(pictureBox1.Image);
        }
    }
}

FreeYoloFace.cs

using OpenCvSharp.Dnn;
using OpenCvSharp;
using System;
using System.Collections.Generic;
using System.Linq;namespace OpenCvSharp_DNN_Demo
{public class FreeYoloFace{float confThreshold;float nmsThreshold;int num_stride = 3;float[] strides = new float[3] { 8.0f, 16.0f, 32.0f };string modelpath;int inpHeight;int inpWidth;List<string> class_names;int num_class;Net opencv_net;Mat BN_image;Mat image;public FreeYoloFace(string modelpath){opencv_net = CvDnn.ReadNetFromOnnx(modelpath);class_names = new List<string> { "face" };num_class = 1;confThreshold = 0.8f;nmsThreshold = 0.5f;inpHeight = 192;inpWidth = 320;}unsafe public List<Face> Detect(Mat image){List<Face> ltFace = new List<Face>();float ratio = Math.Min(1.0f * inpHeight / image.Rows, 1.0f * inpWidth / image.Cols);int neww = (int)(image.Cols * ratio);int newh = (int)(image.Rows * ratio);Mat dstimg = new Mat();Cv2.Resize(image, dstimg, new OpenCvSharp.Size(neww, newh));Cv2.CopyMakeBorder(dstimg, dstimg, 0, inpHeight - newh, 0, inpWidth - neww, BorderTypes.Constant);BN_image = CvDnn.BlobFromImage(dstimg);//配置图片输入数据opencv_net.SetInput(BN_image);//模型推理,读取推理结果Mat[] outs = new Mat[1] { new Mat() };string[] outBlobNames = opencv_net.GetUnconnectedOutLayersNames().ToArray();opencv_net.Forward(outs, outBlobNames);int num_proposal = outs[0].Size(1);int nout = outs[0].Size(2);float* pdata = (float*)outs[0].Data;List<float> confidences = new List<float>();List<Rect> boxes = new List<Rect>();List<int> classIds = new List<int>();for (int n = 0; n < num_stride; n++){int num_grid_x = (int)Math.Ceiling(inpWidth / strides[n]);int num_grid_y = (int)Math.Ceiling(inpHeight / strides[n]);for (int i = 0; i < num_grid_y; i++){for (int j = 0; j < num_grid_x; j++){float box_score = pdata[4];int max_ind = 0;float max_class_socre = 0;for (int k = 0; k < num_class; k++){if (pdata[k + 5] > max_class_socre){max_class_socre = pdata[k + 5];max_ind = k;}}max_class_socre = max_class_socre * box_score;max_class_socre = (float)Math.Sqrt(max_class_socre);if (max_class_socre > confThreshold){float cx = (0.5f + j + pdata[0]) * strides[n];  //cxfloat cy = (0.5f + i + pdata[1]) * strides[n];   //cyfloat w = (float)(Math.Exp(pdata[2]) * strides[n]);   //wfloat h = (float)(Math.Exp(pdata[3]) * strides[n]);  //hfloat xmin = (float)((cx - 0.5 * w) / ratio);float ymin = (float)((cy - 0.5 * h) / ratio);float xmax = (float)((cx + 0.5 * w) / ratio);float ymax = (float)((cy + 0.5 * h) / ratio);int left = (int)((cx - 0.5 * w) / ratio);int top = (int)((cy - 0.5 * h) / ratio);int width = (int)(w / ratio);int height = (int)(h / ratio);confidences.Add(max_class_socre);boxes.Add(new Rect(left, top, width, height));classIds.Add(max_ind);}pdata += nout;}}}int[] indices;CvDnn.NMSBoxes(boxes, confidences, confThreshold, nmsThreshold, out indices);for (int ii = 0; ii < indices.Length; ++ii){int idx = indices[ii];Rect box = boxes[idx];ltFace.Add(new Face(box, confidences[idx]));}outs[0].Dispose();BN_image.Dispose();dstimg.Dispose();return ltFace;}}
}

FaceQualityAssessment.cs

using OpenCvSharp;
using OpenCvSharp.Dnn;
using System.Linq;namespace OpenCvSharp_DNN_Demo
{public class FaceQualityAssessment{Net net;int inpWidth = 112;int inpHeight = 112;float[] mean = new float[] { 0.5f, 0.5f, 0.5f };float[] std = new float[] { 0.5f, 0.5f, 0.5f };public FaceQualityAssessment(string modelpath){net = CvDnn.ReadNetFromOnnx(modelpath);}unsafe public float Detect(Mat cropped){Mat rgbimg = new Mat();Cv2.CvtColor(cropped, rgbimg, ColorConversionCodes.BGR2RGB);Cv2.Resize(rgbimg, rgbimg, new Size(inpWidth, inpHeight));Mat normalized_mat = Normalize(rgbimg);Mat blob = CvDnn.BlobFromImage(normalized_mat);//配置图片输入数据net.SetInput(blob);//模型推理,读取推理结果Mat[] outs = new Mat[1] { new Mat() };string[] outBlobNames = net.GetUnconnectedOutLayersNames().ToArray();net.Forward(outs, outBlobNames);float* pdata = (float*)outs[0].Data;  //形状1x10int length = outs[0].Size(1);float fqa_prob_mean = 0;for (int i = 0; i < length; i++){fqa_prob_mean += pdata[i];}fqa_prob_mean /= length;rgbimg.Dispose();normalized_mat.Dispose();blob.Dispose();outs[0].Dispose();return fqa_prob_mean;}Mat Normalize(Mat src){Mat[] bgr = src.Split();for (int i = 0; i < bgr.Length; ++i){bgr[i].ConvertTo(bgr[i], MatType.CV_32FC1, 1.0 / (255.0 * std[i]), (0.0 - mean[i]) / std[i]);}Cv2.Merge(bgr, src);foreach (Mat channel in bgr){channel.Dispose();}return src;}}
}

下载

源码下载

这篇关于C# OpenCvSharp DNN FreeYOLO 人脸检测人脸图像质量评估的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/590114

相关文章

C#借助Spire.XLS for .NET实现在Excel中添加文档属性

《C#借助Spire.XLSfor.NET实现在Excel中添加文档属性》在日常的数据处理和项目管理中,Excel文档扮演着举足轻重的角色,本文将深入探讨如何在C#中借助强大的第三方库Spire.... 目录为什么需要程序化添加Excel文档属性使用Spire.XLS for .NET库实现文档属性管理Sp

C++,C#,Rust,Go,Java,Python,JavaScript的性能对比全面讲解

《C++,C#,Rust,Go,Java,Python,JavaScript的性能对比全面讲解》:本文主要介绍C++,C#,Rust,Go,Java,Python,JavaScript性能对比全面... 目录编程语言性能对比、核心优势与最佳使用场景性能对比表格C++C#RustGoJavapythonjav

C# 预处理指令(# 指令)的具体使用

《C#预处理指令(#指令)的具体使用》本文主要介绍了C#预处理指令(#指令)的具体使用,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学... 目录1、预处理指令的本质2、条件编译指令2.1 #define 和 #undef2.2 #if, #el

C#实现将Excel工作表拆分为多个窗格

《C#实现将Excel工作表拆分为多个窗格》在日常工作中,我们经常需要处理包含大量数据的Excel文件,本文将深入探讨如何在C#中利用强大的Spire.XLSfor.NET自动化实现Excel工作表的... 目录为什么需要拆分 Excel 窗格借助 Spire.XLS for .NET 实现冻结窗格(Fro

C# Semaphore与SemaphoreSlim区别小结

《C#Semaphore与SemaphoreSlim区别小结》本文主要介绍了C#Semaphore与SemaphoreSlim区别小结,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的... 目录一、核心区别概览二、详细对比说明1.跨进程支持2.异步支持(关键区别!)3.性能差异4.API 差

C# List.Sort四种重载总结

《C#List.Sort四种重载总结》本文详细分析了C#中List.Sort()方法的四种重载形式及其实现原理,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友... 目录1. Sort方法的四种重载2. 具体使用- List.Sort();- IComparable

C#中Trace.Assert的使用小结

《C#中Trace.Assert的使用小结》Trace.Assert是.NET中的运行时断言检查工具,用于验证代码中的关键条件,下面就来详细的介绍一下Trace.Assert的使用,具有一定的参考价值... 目录1、 什么是 Trace.Assert?1.1 最简单的比喻1.2 基本语法2、⚡ 工作原理3

C#中DateTime的格式符的实现示例

《C#中DateTime的格式符的实现示例》本文介绍了C#中DateTime格式符的使用方法,分为预定义格式和自定义格式两类,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值... 目录DateTime的格式符1.核心概念2.预定义格式(快捷方案,直接复用)3.自定义格式(灵活可控

C# IPAddress 和 IPEndPoint 类的使用小结

《C#IPAddress和IPEndPoint类的使用小结》本文主要介绍了C#IPAddress和IPEndPoint类的使用小结,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定... 目录一、核心作用网络编程基础类二、IPAddress 类详解三种初始化方式1. byte 数组初始化2. l

使用C#实现将RTF转换为PDF

《使用C#实现将RTF转换为PDF》RTF(RichTextFormat)是一种通用的文档格式,允许用户在不同的文字处理软件中保存和交换格式化文本,下面我们就来看看如何使用C#实现将RTF转换为PDF... 目录Spire.Doc for .NET 简介安装 Spire.Doc代码示例处理异常总结RTF(R