深入浅出opencv人脸识别,准确率95%,云服务器数据库存储人脸信息,代码全过程讲解以及心得

这篇具有很好参考价值的文章主要介绍了深入浅出opencv人脸识别,准确率95%,云服务器数据库存储人脸信息,代码全过程讲解以及心得。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

此文章记录自己从实现人脸识别到把识别到的数据上传到云端的数据库,随时随地只要有网就能登录服务器,查看人员进出的情况。我会把我记得的所有的错误和经验都分享出来,希望能对大家有所帮助也是对自己的一个总结。

视觉部分:采样,训练,识别


1:人脸采集:

首先输入学号和姓名,设定一个变量存储获取到人脸图片的数量,和存储图片的文件夹,然后打开摄像头开始捕捉人脸。(注意:存储路径的时候学号必须是str类型的)。进入while首先判断摄像头是否已经打开,如果没有就break退出while。

继续while里边,先转换为灰度图片,然后加载opencv库中的一个级联分类器文件,用于检测图像中是否存在人脸,是opencv中比较经典的人脸检测算法之一。

接下来是detectMultiScale函数,获取人脸,返回一个矩阵列表(gray是输入图像(灰度图),1.2表示每次图像缩小的比例为1.2,5表示每个矩形至少应该有5个邻居矩形。函数返回的结果保存在faces中,是一个矩形列表,每个矩形表示一个检测到的人脸的位置和大小)。

接着是判断有两人的情况下,如果face>于1就停止录入,每次只录入一个人脸,然后是绘制矩形框,frame是要绘制矩形框的图像。(x, y)是矩形框的左上角坐标。(x + w, y + h)是矩形框的右下角坐标。color=(0, 255, 0)表示矩形框的颜色,(0, 255, 0)表示绿色。thickness=2表示矩形框的线条粗细为2个像素。

锚出框后,写进数据库里面,便于训练

if __name__ == '__main__':
    face_id = input('请输入学号:')
    face_name = input('请输入姓名:')
    print('请看向摄像头,3秒后开始采集300张人脸图片(可按ESC强制退出)...')
    count = 0  # 统计照片数量
    path = "./Picture_resources/Stu_" + str(face_id)  # 人脸图片数据的储存路径
    # 读取视频
    cap = cv.VideoCapture(0)
    time.sleep(3)  # 给你3s,管理表情
    while True:#捕捉人脸
        flag, frame = cap.read()
        if not flag:
            break
        # 将图片灰度
        gray = cv.cvtColor(frame, cv.COLOR_BGR2GRAY)
        # 加载特征数据
        face_detector = cv.CascadeClassifier('haarcascade_frontalface_default.xml')
        faces = face_detector.detectMultiScale(gray, 1.2, 5)
        for x, y, w, h in faces:
            cv.rectangle(frame, (x, y), (x + w, y + h), color=(0, 255, 0), thickness=2)
            count += 1
            # 显示图片
            cv.imshow('Camera', frame)
        print('已采集成功人脸照片数量为:' + str(count))

2:人脸训练:

首先找到存放图片的文件夹,getImageAndLabels函数接收文件夹路径,

-----root 表示当前正在访问的文件夹路径

-----dirs 表示该文件夹下的子目录名list

------files 表示该文件夹下的文件list(也就是人脸照片)

imageFiles.append追加所有的的照片,准备训练

imagefile.replace('\\','/'),这行代码将\\替换为/,以便正确表示文件路径

id是来自云服务器数据库存储的id,这个点下面再介绍

下面几行就人脸采样类似,遍历检测到的人脸(在变量faces中),并使用切片操作(img_numpy[y:y+h,x:x+w])从输入图像中提取出对应的人脸区域,然后将其添加到人脸样本列表(facesSamples)中,并将对应的标签(id)添加到标签列表(ids)中。这些样本和标签可以用于训练人脸识别模型。返回框出来的人脸和对应的id

然后勇训练对象调用训练识别器 recognizer.train(faces,np.array(ids该方法会使用这些数据训练识别器,生成一个模型,该模型可以根据输入的人脸图像判断该人脸属于哪个标签或 ID。

具体算法实现过程可以参加这篇博客(27条消息) OpenCV人脸识别之LBPH算法(局部二值模式方法)_dongcidacigogogo的博客-CSDN博客

def getImageAndLabels(path):
    facesSamples=[]
    imageFiles = []
    ids = []
    for root, dirs, files in os.walk(path):
        # 遍历文件
        for file in files:
            imageFiles.append(os.path.join(root, file))
    #检测人脸
    face_detector = cv2.CascadeClassifier('haarcascade_frontalface_default.xml')
    #遍历列表中的图片
    count = 0
    for imagefile in imageFiles: #获得各文件夹名字
        imagefile=imagefile.replace('\\','/')
        id = int(getIdfromSql(imagefile.split('/')[2].split('_')[1]))

        PIL_img=Image.open(imagefile).convert('L') #打开图片并且转为灰度图片
        #将图像转换为数组
        img_numpy=np.array(PIL_img,'uint8')
        faces = face_detector.detectMultiScale(img_numpy)

    return ids

if __name__ == '__main__':
    path='./Picture_resources'
    #获取图像数组和id标签数组
    print('开始采集数据...')
    faces,ids=getImageAndLabels(path)
    print('采集数据结束,开始训练数据...')
    #获取训练对象
    recognizer=cv2.face.LBPHFaceRecognizer_create()
    recognizer.train(faces,np.array(ids))
    #保存文件
    recognizer.write('./Trainer/trainer.yml')
    print('训练数据成功!3秒后程序自动关闭...')
    time.sleep(3)

3:人脸识别:

其中get(propId)函数可以用来获取视频的属性,propId=3表示获取帧宽度,propId=4表示获取帧高度,所以video.get(3)返回视频帧的宽度,video.get(4)返回视频帧的高度。

首先读取他们训练好的特征recogizer.read('trainer.yml')

然后打开摄像头获取到人脸,之后调用recogizer.predict(gray[y:y+h, x:x+w])

预测函数,返回了id和置信度,置信度的意思就是可信度,通常情况下,认为小于50 的值是可以接受的,如果该值大于80 则认为差别较大。之后就是用cv的画图函数将预测结果展示出来

好了,整个人脸识别项目就写好了,是不是很简单?主要是我们有了已经封装好的train和predict进行运用,然后用摄像头获取到人脸这个函数去计算人脸的特征加预测即可。虽然这个算法比较简单和久远,但我们还是有必讲这些算法去了解一下,也有便于我们后续理解更多不同的算法。

视频演示在文章最后有链接,感兴趣的可以点击观看。

二:云端数据库

1:人脸采集部分的云端:

首先调用connect连接你的数据库,我这里用的是mysql,

cur.execute(sql1),execute就是执行的意思,把东西传进去让他帮你执行,

con.commit() 是 Python 对 MySQL 数据库的操作中提交事务的方法。当你执行 INSERT、UPDATE 或 DELETE 等语句时,数据不会直接写入数据库,而是先写到缓冲区,等待 commit() 方法被调用后,才会将数据真正写入数据库。这种方式可以保证数据的一致性和完整性。

然后调用cur.fetchall(),它可以一次性获取所有查询结果,返回一个包含所有结果的列表。

然后开始查询数据,首先如果插入的数据信息是已经存在的,判断它的文件夹,进而判断里面是否有图片,如果没有的话就重新录入。如果都存在的,则说明用户已经存在,提醒用户重新输入信息。代码如下:

if student:
    con.close()
    flag = 2
    return flag
result = PutDatatoSql(face_name, face_id)
if result == 1:
    break
elif result == 2:
    # 可能存在数据库有记录 但是图像资源被删掉了,这种情况重新录入
    if not os.path.exists('./Picture_resources/Stu_' + str(face_id)):  # 文件夹是否存在
        break
    elif not os.listdir("./Picture_resources/Stu_" + str(face_id)):  # 文件夹里面是否有文件
        break
    else:
        print('该用户已存在!')

但是如果你传入的数据是很多小数点的,varchar无法处理,则抛出异常,print('插入数据失败')

con.rollback() 是 Python 中 MySQL 数据库模块 mysql-connector-python 中的一个方法,用于撤销自上次提交以来所做的所有更改。

except Exception as e:
    print(e)
     
    print('插入数据失败')
    flag = 0
    return flag

2:人脸训练部分的云端:

主要是索引学号,首先什么人脸训练部分代码中,把文件夹的路径的切分结果(也就是学号)传给getIdfromSql(sno),去获取这个学号的图片信息(注意:在人脸采集的时候输入了学号和姓名,学号用来获取图像去训练,姓名是在预测的时候用到的用来显示预测结果的)

cur.fetchone() 看函数名应该看得出来,大概意思就是fetch(获取)one(一)个什么东西。功能是:返回结果集中的第一行数据(也就是自增长的id),因为是通过学号(sno)查询学生ID,所以查询结果只有一行数据,因此使用fetchone() 从结果集中获取该行数据,并将其赋值给 student 变量。

def getIdfromSql(sno):
    con = pymysql.connect(host='localhost', database='test', user='root', password='123456', port=3306)
    # 创建游标对象
    cur = con.cursor()
    # 编写查询的sql
    sql = 'select id from t_stu where sno='+sno
    # 执行sql
    try:
        cur.execute(sql)
        # 处理结果集
        student = cur.fetchone()
        id = student[0]
        return id
    except Exception as e:
        print(e)
        print('查询所有数据失败')
    finally:
        con.close()

3:人脸识别部分的云端:

识别部分就只有获取学生信息了。重点是students = cur.fetchall()这一行代码,获取到所有数据库的结果后,获取到id号对应的名字,用于结果显示

def getDataFromSql():
    names = {}
    # 创建连接
    con = pymysql.connect()
    # 创建游标对象
    cur = con.cursor()
    # 编写查询的sql
    sql = '   '
    # 执行sql
    try:
        cur.execute(sql)
        # 处理结果集
        students = cur.fetchall()
        for student in students:
            id = student[0]
            sname = student[1]
            sno = student[2]
            names[int(id)] = sname
    except Exception as e:
        print(e)
        print('查询所有数据失败')
    finally:
        # 关闭连接
        con.close()
        return names

另外,在云数据库中,刚开始连不上navicat,因为在图形界面操作数据库简单点。但是刚开始我是连不上的,因为端口号问题,这里面我刚开始是用宝塔来操作服务器的,后来发现宝塔那边放行的端口号,服务器上面没有更新整个端口号(还有字符也要慎重选择)。

当你连上navicat后,你又发现数据库是无法操作的,这里全都在终端敲命令解决的,刚开始想在navicat设置权限的,但是一直说拒绝访问,这一点我花了很多时间找了各种资料,最后弄好了,但是这过程也会帮助你学到很多的东西。

这个是数据库的人脸信息

深入浅出opencv人脸识别,准确率95%,云服务器数据库存储人脸信息,代码全过程讲解以及心得

下面是一个简单的流程图:总体的代码在上面详细的介绍了

深入浅出opencv人脸识别,准确率95%,云服务器数据库存储人脸信息,代码全过程讲解以及心得

录制人脸加训练点击此查看视频演示

识别视频演示点击这里

完整代码链接:(创造不易~)

https://mbd.pub/o/bread/ZJqUlp5v文章来源地址https://www.toymoban.com/news/detail-462062.html

到了这里,关于深入浅出opencv人脸识别,准确率95%,云服务器数据库存储人脸信息,代码全过程讲解以及心得的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • 集成学习与模型融合:如何提高语音识别准确率

    语音识别技术是人工智能领域的一个重要研究方向,它涉及到自然语言处理、信号处理、机器学习等多个领域的知识。随着大数据时代的到来,语音识别技术的发展也受益于大量的数据和高性能计算资源的支持。然而,面对复杂多样的语音数据,传统的单模型方法已经不能满

    2024年02月20日
    浏览(62)
  • 语音识别的数据集构建:如何提高识别准确率和效率

    语音识别,也被称为语音转文本(Speech-to-Text),是一种将语音信号转换为文本信息的技术。随着人工智能、大数据和云计算等技术的发展,语音识别技术在各个领域得到了广泛应用,如智能家居、智能汽车、虚拟助手、搜索引擎等。 在语音识别技术中,数据集构建是一个至关

    2024年04月10日
    浏览(44)
  • 利用Adam优化算法进行语音识别任务:提升模型准确率

    作者:禅与计算机程序设计艺术 语音识别是人工智能领域中的一个重要应用,近年来随着深度学习算法的快速发展,语音识别技术也取得了长足的进步。在语音识别任务中,训练模型需要大量的数据和计算资源,而且模型的准确性也是至关重要的。因此,如何提高模型的准确

    2024年02月09日
    浏览(54)
  • 基于深度学习的多模态语音识别:如何提高语音识别准确率和鲁棒性

    作者:禅与计算机程序设计艺术 随着语音识别技术的发展,采用多种模态(声学、语言模型、视觉特征等)进行联合建模,基于深度学习的多模态语音识别取得了新进展。传统的声学模型或手工特征工程方法已经无法满足实时、高精度、低延迟的需求,多模态语音识别需要解决

    2024年02月13日
    浏览(70)
  • python 识别图片验证码/滑块验证码准确率极高的 ddddocr 库

    验证码的种类有很多,它是常用的一种反爬手段,包括:图片验证码,滑块验证码,等一些常见的验证码场景。 识别验证码的python 库有很多,用起来也并不简单,这里推荐一个简单实用的识别验证码的库 ddddocr (带带弟弟ocr)库. python 版本要求小于等于python3.9 版本 pip 安装 下

    2023年04月08日
    浏览(42)
  • python 识别图片验证码/滑块验证码准确率极高的 ddddorc 库

    前言 验证码的种类有很多,它是常用的一种反爬手段,包括:图片验证码,滑块验证码,等一些常见的验证码场景。识别验证码的python 库有很多,用起来也并不简单,这里推荐一个简单实用的识别验证码的库 ddddocr (带带弟弟ocr)库. 环境准备 python 版本要求小于等于python3.9 版

    2024年02月03日
    浏览(45)
  • 深入浅出线程池

    线程 (thread)是操作系统能够进行运算调度的最小单位。它被包含在进程之中,是进程中的实际 运作单位。一条线程指的是进程中一个单一顺序的控制流,一个进程中可以并发多个线程,每条线 程并行执行不同的任务。 既然我们创建了线程,那为何我们直接调用方法和我们调

    2024年02月08日
    浏览(50)
  • 深入浅出 Typescript

    TypeScript 是 JavaScript 的一个超集,支持 ECMAScript 6 标准(ES6 教程)。 TypeScript 由微软开发的自由和开源的编程语言。 TypeScript 设计目标是开发大型应用,它可以编译成纯 JavaScript,编译出来的 JavaScript 可以运行在任何浏览器上。 TypeScript JavaScript JavaScript 的超集,用于解决大型

    2024年02月14日
    浏览(52)
  • 深入浅出前端本地储存

    2021 年,如果你的前端应用,需要在浏览器上保存数据,有三个主流方案: Cookie Web Storage (LocalStorage) IndexedDB 这些方案就是如今应用最广、浏览器兼容性最高的三种前端储存方案 今天这篇文章就聊一聊这三种方案的历史,优缺点,以及各自在今天的适用场景 文章在后面还会提

    2024年04月17日
    浏览(84)
  • 深入浅出Kafka

    这个主题 武哥漫谈IT ,作者骆俊武 讲得更好 首先我们得去官网看看是怎么介绍Kafka的: https://kafka.apache.org/intro Apache Kafka is an open-source distributed event streaming platform. 翻译成中文就是:Apache Kafka 是一个开源的分布式流处理平台。 Kafka 不是一个消息系统吗?为什么被称为分布式

    2023年04月11日
    浏览(73)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包