C#打开摄像头后获取图片,调用face_recognition进行人脸识别

news2024/11/25 0:49:06

运行效果如截图:左边和保存的图片做对比,打印相似度,部分打印内容为python中的打印输出,可以用来做结果判断。右边打开摄像头后,可以单张图片进行人脸识别,或者一直截图镜头中的图片进行比对。期中python使用开源的face_recognition进行人脸识别的。

想了解更多我发过的C#的博客,参考:C#基础知识体系框架图,及起对应我发过的博客_花开莫与流年错_的博客-CSDN博客

下面我先介绍python部分

官网参考连接:Windows Installation Tutorial · Issue #175 · ageitgey/face_recognition · GitHub

对应github网址:face_recognition/README_Simplified_Chinese.md at master · ageitgey/face_recognition · GitHub

需要先下载CMake,在官网下载即可:Download | CMake

下载python3安装,安装结束时勾选所有用户命令使用:Download Python | Python.org

pip下载地址:pip · PyPI

pip安装:下载解压后,到该目录输入

python setup.py install

pip升级:

pip3 install --upgrade pip
pip install pip	或者用这个试试

安装人脸识别及依赖

pip install dlib
pip install face_recognition
pip install opencv-contrib-python

执行测试用例(期中第一个图片为保存的图片,第二个图片为我的摄像头实时保存的图片)

import face_recognition
import sys
# face_recognition --cpus 4 ./pictures_of_people_i_know/ ./unknown_pictures/

known_image = face_recognition.load_image_file("图片/11.jpg")
unknown_image = face_recognition.load_image_file("xx.jpg")

biden_encoding = face_recognition.face_encodings(known_image)[0]
image_encoding = face_recognition.face_encodings(unknown_image)
if len(image_encoding) > 0:
    unknown_encoding = image_encoding[0]
else:
    print("no")
    sys.exit(0)

results = face_recognition.compare_faces([biden_encoding], unknown_encoding)
face_distances = face_recognition.face_distance([biden_encoding], unknown_encoding)

# print(results)
if results[0] == True and face_distances < 0.4:
    print("yes")
    #sys.exit(1)             # 返回1
else:
    print("no")
    #sys.exit(0)

print("人脸相似度")
print(face_distances)

#sleep(1)
#print(text)

#return results[0]

运行及错误处理

1、python退出运行并返回退出值

import sys
sys.exit(0)

2、C#调用python实现人脸识别,执行接收后获取python打印值

using (System.Diagnostics.Process p = new System.Diagnostics.Process())
{
    p.StartInfo.FileName = @"python3"; //python会运行错误,提示没有face_recognition,需要制定python3的安装路径
    p.StartInfo.Arguments = cmd;//python命令的参数
    p.StartInfo.UseShellExecute = false;
    p.StartInfo.RedirectStandardOutput = true;
    p.StartInfo.RedirectStandardInput = true;
    p.StartInfo.RedirectStandardError = true;
    p.StartInfo.CreateNoWindow = true;
    p.Start();//启动进程
    Console.WriteLine("Start");

    // p.StandardInput.WriteLine(@"exit()");
    StreamReader reader = p.StandardOutput;
    if (reader == null)
        Console.WriteLine("reader is null");
    else
    {
        string output = reader.ReadToEnd();  // ReadToEnd/ReadLine
        Console.WriteLine("face output : " + output);
        string error = p.StandardError.ReadToEnd();
        if (error != null && error != "")
            Console.WriteLine("face err : " + error);
    }
    p.WaitForExit(); // 等待控制台程序执行完成
    Console.WriteLine("执行完毕!");
}

偶尔运行报错:IndexError: list index out of range\r\n"

# 不一定有人脸,所以需要先判断是否有人脸,有才对比相似度
image_encoding = face_recognition.face_encodings(unknown_image)
if len(image_encoding) > 0:
    unknown_encoding = image_encoding[0]
else:
    print("no")
    sys.exit(0)

C#完整代码

1、MainForm窗体显示部分


namespace Study_CSharp.摄像头
{
    partial class Video
    {
        /// <summary>
        /// Required designer variable.
        /// </summary>
        private System.ComponentModel.IContainer components = null;

        /// <summary>
        /// Clean up any resources being used.
        /// </summary>
        /// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
        protected override void Dispose(bool disposing)
        {
            if (disposing && (components != null))
            {
                components.Dispose();
            }
            base.Dispose(disposing);
        }

        #region Windows Form Designer generated code

        /// <summary>
        /// Required method for Designer support - do not modify
        /// the contents of this method with the code editor.
        /// </summary>
        private void InitializeComponent()
        {
            this.videoSourcePlayer1 = new AForge.Controls.VideoSourcePlayer();
            this.button1 = new System.Windows.Forms.Button();
            this.button2 = new System.Windows.Forms.Button();
            this.button3 = new System.Windows.Forms.Button();
            this.comboBox1 = new System.Windows.Forms.ComboBox();
            this.button4 = new System.Windows.Forms.Button();
            this.button5 = new System.Windows.Forms.Button();
            this.SuspendLayout();
            // 
            // videoSourcePlayer1
            // 
            this.videoSourcePlayer1.Location = new System.Drawing.Point(41, 90);
            this.videoSourcePlayer1.Name = "videoSourcePlayer1";
            this.videoSourcePlayer1.Size = new System.Drawing.Size(932, 571);
            this.videoSourcePlayer1.TabIndex = 7;
            this.videoSourcePlayer1.Text = "videoSourcePlayer1";
            this.videoSourcePlayer1.VideoSource = null;
            // 
            // button1
            // 
            this.button1.Font = new System.Drawing.Font("微软雅黑", 12F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point, ((byte)(134)));
            this.button1.Location = new System.Drawing.Point(704, 22);
            this.button1.Name = "button1";
            this.button1.Size = new System.Drawing.Size(144, 47);
            this.button1.TabIndex = 8;
            this.button1.Text = "关闭摄像头";
            this.button1.UseVisualStyleBackColor = true;
            this.button1.Click += new System.EventHandler(this.button1_Click);
            // 
            // button2
            // 
            this.button2.Font = new System.Drawing.Font("微软雅黑", 12F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point, ((byte)(134)));
            this.button2.Location = new System.Drawing.Point(364, 22);
            this.button2.Name = "button2";
            this.button2.Size = new System.Drawing.Size(144, 47);
            this.button2.TabIndex = 9;
            this.button2.Text = "拍照";
            this.button2.UseVisualStyleBackColor = true;
            this.button2.Click += new System.EventHandler(this.button2_Click);
            // 
            // button3
            // 
            this.button3.Font = new System.Drawing.Font("微软雅黑", 12F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point, ((byte)(134)));
            this.button3.Location = new System.Drawing.Point(534, 22);
            this.button3.Name = "button3";
            this.button3.Size = new System.Drawing.Size(144, 47);
            this.button3.TabIndex = 10;
            this.button3.Text = "保存图片";
            this.button3.UseVisualStyleBackColor = true;
            this.button3.Click += new System.EventHandler(this.button3_Click);
            // 
            // comboBox1
            // 
            this.comboBox1.DropDownHeight = 100;
            this.comboBox1.FormattingEnabled = true;
            this.comboBox1.ItemHeight = 15;
            this.comboBox1.Location = new System.Drawing.Point(874, 37);
            this.comboBox1.Name = "comboBox1";
            this.comboBox1.Size = new System.Drawing.Size(121, 23);
            this.comboBox1.TabIndex = 11;
            this.comboBox1.SelectedIndexChanged += new System.EventHandler(this.comboBox1_SelectedIndexChanged);
            // 
            // button4
            // 
            this.button4.Font = new System.Drawing.Font("微软雅黑", 12F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point, ((byte)(134)));
            this.button4.Location = new System.Drawing.Point(24, 22);
            this.button4.Name = "button4";
            this.button4.Size = new System.Drawing.Size(144, 47);
            this.button4.TabIndex = 12;
            this.button4.Text = "人脸识别";
            this.button4.UseVisualStyleBackColor = true;
            this.button4.Click += new System.EventHandler(this.button4_Click);
            // 
            // button5
            // 
            this.button5.Font = new System.Drawing.Font("微软雅黑", 12F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point, ((byte)(134)));
            this.button5.Location = new System.Drawing.Point(194, 22);
            this.button5.Name = "button5";
            this.button5.Size = new System.Drawing.Size(144, 47);
            this.button5.TabIndex = 13;
            this.button5.Text = "实时扫描";
            this.button5.UseVisualStyleBackColor = true;
            this.button5.Click += new System.EventHandler(this.button5_Click);
            // 
            // Video
            // 
            this.AutoScaleDimensions = new System.Drawing.SizeF(8F, 15F);
            this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
            this.ClientSize = new System.Drawing.Size(1012, 673);
            this.Controls.Add(this.button5);
            this.Controls.Add(this.button4);
            this.Controls.Add(this.comboBox1);
            this.Controls.Add(this.button3);
            this.Controls.Add(this.button2);
            this.Controls.Add(this.button1);
            this.Controls.Add(this.videoSourcePlayer1);
            this.Name = "Video";
            this.Text = "video";
            this.ResumeLayout(false);

        }

        #endregion
        private AForge.Controls.VideoSourcePlayer videoSourcePlayer1;
        private System.Windows.Forms.Button button1;
        private System.Windows.Forms.Button button2;
        private System.Windows.Forms.Button button3;
        private System.Windows.Forms.ComboBox comboBox1;
        private System.Windows.Forms.Button button4;
        private System.Windows.Forms.Button button5;
    }
}

2、窗体中代码处理部分

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using System.IO;

using AForge;
using AForge.Controls;
using AForge.Video;
using AForge.Video.DirectShow;


namespace Study_CSharp.摄像头
{
    public partial class Video : Form
    {
        FilterInfoCollection videoDevices;//摄像头设备集合
        VideoCaptureDevice videoSource;//捕获设备源
        Bitmap img;//处理图片

        public Video()
        {
            InitializeComponent();
            button3.Enabled = false;
            //先检测电脑所有的摄像头
            videoDevices = new FilterInfoCollection(FilterCategory.VideoInputDevice);
            OpenVideo(1);
            comboBox1.BeginUpdate();
            for (int i = 1; i <= videoDevices.Count; i++)
            {
                comboBox1.Items.Add("摄像头" + i);
            }
            comboBox1.EndUpdate();
            if (videoDevices.Count <= 0)
            {
                MessageBox.Show("没有摄像头");
            }
            else{
                comboBox1.Text = "摄像头1";
            }
        }

        private void button1_Click(object sender, EventArgs e)
        {
            if (button1.Text == "打开摄像头")
            {
                OpenVideo(1);
                button1.Text = "关闭摄像头";
            }
            else
            {
                ShutCamera();
                button1.Text = "打开摄像头";
            }
        }
        // 打开摄像头
        public void OpenVideo(int n)
        {
            if (videoDevices.Count >= n)
            {
                videoSource = new VideoCaptureDevice(videoDevices[n - 1].MonikerString);
                videoSourcePlayer1.VideoSource = videoSource;
                videoSourcePlayer1.Start();
            }
        }
        // 关闭并释放摄像头
        public void ShutCamera()
        {
            if (videoSourcePlayer1.VideoSource != null)
            {
                videoSourcePlayer1.SignalToStop();
                videoSourcePlayer1.WaitForStop();
                videoSourcePlayer1.VideoSource = null;
            }
        }

        private void button2_Click(object sender, EventArgs e)
        {
            img = videoSourcePlayer1.GetCurrentVideoFrame();//拍摄
            button3.Enabled = true; // 开启“保存”功能
        }

        // "保存"按钮click事件
        private void button3_Click(object sender, EventArgs e)
        {
            SaveImage(true);
        }
        public void SaveImage(bool changeName = false)
        {
            if (img == null)
                return;
            try
            {
                //以当前时间为文件名,保存为jpg格式
                //图片路径在程序bin目录下的Debug下
                TimeSpan tss = DateTime.UtcNow - new DateTime(1970, 1, 1, 0, 0, 0, 0);
                long a = Convert.ToInt64(tss.TotalMilliseconds) / 1000;  //以秒为单位
                if (changeName)
                    img.Save(string.Format("{0}.jpg", a.ToString()));
                else
                    img.Save("xx.jpg");
                button3.Enabled = false;
            }
            catch (Exception ex)
            {
                MessageBox.Show(ex.Message);
            }
        }
        private void comboBox1_SelectedIndexChanged(object sender, EventArgs e)
        {
            string str = comboBox1.Text;
            int camr = Convert.ToInt32(str[3]) - '0'; // Encoding.ASCII.GetBytes(str);
            if (button1.Text != "打开摄像头" && camr <= videoDevices.Count)
            {
                ShutCamera();
                OpenVideo(camr);
            }
        }

        private void button4_Click(object sender, EventArgs e)
        {
            RunPythonFaceRecgn("test.py");
        }
        // 调用系统命令
        void RunPythonFaceRecgn(string cmd)
        {
            try
            {
                using (System.Diagnostics.Process p = new System.Diagnostics.Process())
                {
                    p.StartInfo.FileName = @"python3"; //python会运行错误,提示没有face_recognition,需要制定python3的安装路径
                    p.StartInfo.Arguments = cmd;//python命令的参数
                    p.StartInfo.UseShellExecute = false;
                    p.StartInfo.RedirectStandardOutput = true;
                    p.StartInfo.RedirectStandardInput = true;
                    p.StartInfo.RedirectStandardError = true;
                    p.StartInfo.CreateNoWindow = true;
                    p.Start();//启动进程
                    Console.WriteLine("Start");

                    // p.StandardInput.WriteLine(@"exit()");
                    StreamReader reader = p.StandardOutput;
                    if (reader == null)
                        Console.WriteLine("reader is null");
                    else
                    {
                        string output = reader.ReadToEnd();  // ReadToEnd/ReadLine
                        Console.WriteLine("face output : " + output);
                        string error = p.StandardError.ReadToEnd();
                        if (error != null && error != "")
                            Console.WriteLine("face err : " + error);
                    }
                    p.WaitForExit(); // 等待控制台程序执行完成
                    Console.WriteLine("执行完毕!");
                }
            }
            catch (Exception e)
            {
                Console.WriteLine(e.Message);
            }
        }

        bool RunFaceRecgn = false;
        private void button5_Click(object sender, EventArgs e)
        {
            if (RunFaceRecgn)
                RunFaceRecgn = false;
            else
                RunFaceRecgn = true;

            Task.Run(() => {
                while (RunFaceRecgn)
                {
                    img = videoSourcePlayer1.GetCurrentVideoFrame();//拍摄
                    SaveImage();
                    RunPythonFaceRecgn("test.py");
                    System.Threading.Thread.Sleep(500);
                }
            });
        }
    }
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/86775.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

ReSharper添加对最新C#11特性的支持

ReSharper添加对最新C#11特性的支持 C#11 UTF-8文字-增加了对UTF-8文字的基本支持。代码分析现在建议对文字使用u8后缀&#xff0c;而不是System.Text.Encoding.UTF8.GetBytes()方法或具有适当UTF8符号的字节数组。还有一组UTF-8文本的编译器警告和错误。 文件本地类型-添加了对…

服务器公网带宽1M能同时接受多少人访问?

文章目录1、什么是服务器的带宽?2、服务器带宽多少?3、服务器带宽1M能同时接受多少人访问?1、什么是服务器的带宽? 在服务器托管中&#xff0c;服务器带宽指在特定时间段从或向网站/服务器传输的数据量&#xff0c;例如&#xff0c;单月内的累积消耗“带宽”&#xff0c;实…

【开源掌机】百问网DShanMCU-Mio开源掌机(爻-澪)项目,完美支持运行10多个模拟器!

众筹说明 定金翻倍&#xff0c;即定金19.9元&#xff0c;在付尾款时可抵40元(成品售价不会超过120元)&#xff01;达标当天就开搞&#xff0c;满100人加速搞尽量在年前发货&#xff0c;让大家先玩起来&#xff01;如果不达标则原路退款&#xff0c;项目取消。 众筹时间&#…

利用Matlab进行图像分割和边缘检测

本文章包含以下内容&#xff1a; 1、灰度阀值分割 (1)单阈值分割图像 先将一幅彩色图像转换为灰度图像&#xff0c;显示其直方图&#xff0c;参考直方图中灰度的分布&#xff0c;尝试确定阈值&#xff1b;应反复调节阈值的大小&#xff0c;直至二值化的效果最为满意…

LDR6035PD快充快放带数据还要啥莲花清翁

随着Type-C的普及和推广&#xff0c;目前市面上的移动电源正在慢慢淘汰micro-USB接口&#xff0c;逐渐都更新成了Type-C接口&#xff0c;micro-USB接口从2007年上市&#xff0c;已经陪伴我们走过十多个年头&#xff0c;自从2015年Type-C登场&#xff0c;micro-USB也开始渐渐淡出…

写给前端开发者的「Promise备忘手册」

前言 大家好&#xff0c;我是HoMeTown&#xff0c;Promise想必大家都知道&#xff0c;在平时的开发工程中也经常会有用到&#xff0c;但是Promise作为ES6的重要特性&#xff0c;其实还拥有很多丰富的知识&#xff0c;本文面向比较初级一些的同学&#xff0c;可以帮你搞懂Promi…

金庸群侠传3DUnity重置入门-Mods开发

金庸3DUnity重置入门系列文章 金庸3dUnity重置入门 - lua 语法 金庸3dUnity重置入门 - UniTask插件 金庸3dUnity重置入门 - Mods开发 金庸3dUnity重置入门 - Cinemachine 动画 金庸3dUnity重置入门 - 大世界实现方案 金庸3dUnity重置入门 - 素材极限压缩 (部分可能放到付…

[附源码]Nodejs计算机毕业设计基于web的社团管理系统Express(程序+LW)

该项目含有源码、文档、程序、数据库、配套开发软件、软件安装教程。欢迎交流 项目运行 环境配置&#xff1a; Node.js Vscode Mysql5.7 HBuilderXNavicat11VueExpress。 项目技术&#xff1a; Express框架 Node.js Vue 等等组成&#xff0c;B/S模式 Vscode管理前后端分…

机器学习——01基础知识

机器学习——01基础知识 github地址&#xff1a;https://github.com/yijunquan-afk/machine-learning 参考资料 [1] 庞善民.西安交通大学机器学习导论2022春PPT [2] 周志华. 机器学习.北京:清华大学出版社,2016 [3] AIlearning 一、机器学习算法的应用 目前&#xff0c;机…

【Redis】集合Set和底层实现

文章目录Redis 集合(Set)Set简介常用命令应用场景共同关注实例整数集合整数集合介绍整数集合的升级哈希表哈希表的原理和实现Redis中的哈希表rehash渐进式rehashRedis 集合(Set) Set简介 Redis set对外提供的功能与list类似是一个列表的功能&#xff0c;特殊之处在于set是可以…

多维时序 | MATLAB实现GRU多变量时间序列预测

✅作者简介&#xff1a;热爱科研的Matlab仿真开发者&#xff0c;修心和技术同步精进&#xff0c;matlab项目合作可私信。 &#x1f34e;个人主页&#xff1a;Matlab科研工作室 &#x1f34a;个人信条&#xff1a;格物致知。 更多Matlab仿真内容点击&#x1f447; 智能优化算法 …

c语言中fread,fgets等取文件字符的缓存空间小出现问题

一种奇怪现象 #include <stdio.h> #include <stdlib.h> #include<windows.h>int main(void){int i;printf("hello\n");fflush(stdout); //当没有这部刷新&#xff0c;hello会和end等到时间一起输出Sleep(2000); //windowsa.h中的Sleep&#…

某研究生不写论文竟研究起了算命?

起因 大约一个月前&#xff0c;在学校大病一场&#xff08;不知道是不是&#x1f411;了&#xff0c;反正在学校每天核酸没检测出来&#xff09;在宿舍休息了整整一周。当时因为发烧全身疼所以基本一直躺着刷刷视频。看了一周倪海厦老师讲的天纪&#xff0c;人纪感悟颇多&…

央企招聘:中国航空油料集团2023公开招聘

一、公司简介 中国航空油料集团有限公司&#xff08;以下简称“中国航油”&#xff09;成立于2002年10月11日&#xff0c;是以原中国航空油料总公司为基础组建的国有大型航空运输服务保障企业&#xff0c;是国内最大的集航空油品采购、运输、储存、检测、销售、加注为一体的航…

Spring Boot打成jar包后运行及配置文件的问题

Maven打包 因为Spring Boot项目内置Tomcat&#xff0c;所以可以打成一个jar包直接运行&#xff0c;而不必再需要安装Tomcat了。 如果用IDEA打包&#xff0c;还得先添加Artifacts&#xff1a; 然后再选择‘Main Class’ 显然比较麻烦&#xff0c;而且每次导入项目都得重新添加…

高频功率放大器工作原理总结(高频和低频功率放大器的区别)

高频功率放大器处在发射机的末级&#xff0c;主要作用是把高频已调拨信号进行功率放大&#xff0c;满足发送功率的要求&#xff0c;然后通过天线辐射到空间&#xff0c;保证一定区域接收机能够接收到信号电平。 高频功率放大器是通信系统中发送装置的组件&#xff0c;按照频带的…

【DOTS学习笔记】Cache层级结构与排队管理

目录前言如何理解L1,L2,L3级缓存的树形结构设计排队的烦恼现实中的排队烦恼计算机程序设计中的排队队列类型前言 本文是Metaverse大衍神君的《DOTS之路》系列课程的学习笔记 如何理解L1,L2,L3级缓存的树形结构设计 排队的烦恼 现实中的排队烦恼 这是一张关于排队的图&#xf…

论文速递:AAAI 2023 | 优图16篇论文速览,含多标签分类、姿态估计、目标检测、HOI、小样本学习等研究方向

近日&#xff0c;AAAI 2023&#xff08;Association for the Advancement of Artificial Intelligence&#xff09;国际先进人工智能协会公布了录用结果&#xff0c;本届会议共有8777篇投稿&#xff0c;录用1721篇&#xff0c;录用率19.6%。 AAAI是人工智能领域的主要学术组织之…

[go 语言学习笔记] 7天用Go从零实现分布式缓存GeeCache 「持续更新中」

说明 本文用于记录学习 go 语言过程中的笔记, 文中的代码都是在文本中敲出来的伪代码, 并不能直接运行, 如有需要可以参考原文链接. 本文的整体思路是对原系列教程阅读后的复盘. 关于本文参考的 学习教程 可以访问原教程链接: 7天用Go从零实现分布式缓存GeeCache 本文如有…

文本检测识别技术在合合信息的应用实务解决方案

合合信息保险行业全业务流程数字化解决方案 合合信息依托AI大数据&#xff0c;打造了保险行业全业务流程数字化解决方案&#xff1a;OCR智能分类识别文档、表格、卡证、票据、合同等&#xff0c;替代人工录入&#xff0c;图像智能质检优化&#xff0c;实现投保、核保、理赔、合…