当前位置: 首页 > news >正文

OpenCV 引擎:驱动实时应用开发的科技狂飙

OpenCV 是计算机视觉领域超实用的开源库。它能帮你实现图像、视频处理,像实时检测人脸、跟踪目标、处理图像。无论是安防监控、自动驾驶,还是趣味手势识别,OpenCV 都能大显身手!

目录

一、背景

二、OpenCV 环境搭建

2.1 安装 Python

2.2 安装 OpenCV 库

三、OpenCV 基本操作

3.1 图像读取与显示

3.2 视频捕获与显示

四、实时目标检测

4.1 Haar 级联分类器

4.2 YOLO(You Only Look Once)

五、实时目标跟踪

5.1 KCF(Kernelized Correlation Filters)跟踪器

六、实时图像处理

6.1 图像滤波

6.2 边缘检测

七、实时应用案例

7.1 智能安防监控系统

7.2 手势识别系统

八、小结


一、背景

OpenCV 作为计算机视觉领域的开源库,凭借其丰富的算法和高效的性能,在实时应用开发中占据重要地位。实时应用要求系统能够在短时间内对输入数据进行处理并给出反馈,OpenCV 的多种功能正好满足了这些需求,如安防监控需快速检测目标,自动驾驶要实时识别道路信息等。

二、OpenCV 环境搭建

2.1 安装 Python

Python 是使用 OpenCV 的常用语言,其安装步骤如下:

步骤操作内容说明
1访问 Python 官方网站(Download Python | Python.org)可根据操作系统选择合适的 Python 版本,建议使用 Python 3.9 及以上版本
2下载对应操作系统的安装包如 Windows 选择.exe 文件,Linux 选择源码包或使用包管理器安装
3运行安装程序安装过程中勾选 “Add Python to PATH”,方便后续使用

2.2 安装 OpenCV 库

安装 OpenCV 库可通过 pip 命令完成,具体如下:

库名称安装命令用途
opencv - pythonpip install opencv - python基础的 OpenCV 库,包含核心功能
opencv - contrib - pythonpip install opencv - contrib - python包含额外的贡献模块,如一些实验性算法和功能

三、OpenCV 基本操作

3.1 图像读取与显示

import cv2

# 读取图像
image = cv2.imread('test.jpg')

# 显示图像
cv2.imshow('Image', image)

# 等待按键事件
cv2.waitKey(0)

# 关闭所有窗口
cv2.destroyAllWindows()
函数作用参数说明
cv2.imread()读取图像文件第一个参数为图像文件路径,第二个参数可指定读取模式(如灰度模式等)
cv2.imshow()显示图像第一个参数为窗口名称,第二个参数为要显示的图像数据
cv2.waitKey()等待按键事件参数为等待时间(毫秒),0 表示无限等待
cv2.destroyAllWindows()关闭所有打开的窗口无参数

3.2 视频捕获与显示

import cv2

# 打开摄像头
cap = cv2.VideoCapture(0)

while True:
    # 读取一帧视频
    ret, frame = cap.read()

    if not ret:
        break

    # 显示帧
    cv2.imshow('Video', frame)

    # 按 'q' 键退出循环
    if cv2.waitKey(1) & 0xFF == ord('q'):
        break

# 释放摄像头并关闭所有窗口
cap.release()
cv2.destroyAllWindows()
函数作用参数说明
cv2.VideoCapture()打开视频捕获设备参数可以是摄像头编号(如 0 表示默认摄像头)或视频文件路径
cap.read()读取一帧视频返回两个值,ret 表示是否成功读取,frame 为读取的帧数据
cap.release()释放视频捕获设备无参数

四、实时目标检测

4.1 Haar 级联分类器

import cv2

# 加载人脸分类器
face_cascade = cv2.CascadeClassifier(cv2.data.haarcascades + 'haarcascade_frontalface_default.xml')

# 打开摄像头
cap = cv2.VideoCapture(0)

while True:
    ret, frame = cap.read()

    if not ret:
        break

    # 转换为灰度图像
    gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)

    # 检测人脸
    faces = face_cascade.detectMultiScale(gray, 1.1, 4)

    # 在检测到的人脸周围绘制矩形
    for (x, y, w, h) in faces:
        cv2.rectangle(frame, (x, y), (x + w, y + h), (255, 0, 0), 2)

    # 显示帧
    cv2.imshow('Face Detection', frame)

    if cv2.waitKey(1) & 0xFF == ord('q'):
        break

# 释放摄像头并关闭所有窗口
cap.release()
cv2.destroyAllWindows()
步骤操作说明
1加载分类器使用 cv2.CascadeClassifier() 加载预训练的分类器文件
2读取视频帧利用 cv2.VideoCapture() 和 cap.read() 读取摄像头视频帧
3转换为灰度图像使用 cv2.cvtColor() 将彩色图像转换为灰度图像,提高检测效率
4目标检测调用 detectMultiScale() 方法进行目标检测,返回检测到的目标矩形框信息
5绘制矩形框使用 cv2.rectangle() 在检测到的目标周围绘制矩形框

4.2 YOLO(You Only Look Once)

import cv2
import numpy as np

# 加载模型配置和权重文件
net = cv2.dnn.readNet('yolov3.weights', 'yolov3.cfg')

# 加载类别名称
classes = []
with open('coco.names', 'r') as f:
    classes = [line.strip() for line in f.readlines()]

# 打开摄像头
cap = cv2.VideoCapture(0)

while True:
    ret, frame = cap.read()

    if not ret:
        break

    height, width, _ = frame.shape

    # 准备输入图像
    blob = cv2.dnn.blobFromImage(frame, 1 / 255.0, (416, 416), swapRB=True, crop=False)
    net.setInput(blob)

    # 获取输出层名称
    output_layer_names = net.getUnconnectedOutLayersNames()

    # 前向传播
    outputs = net.forward(output_layer_names)

    boxes = []
    confidences = []
    class_ids = []

    # 处理输出结果
    for output in outputs:
        for detection in output:
            scores = detection[5:]
            class_id = np.argmax(scores)
            confidence = scores[class_id]

            if confidence > 0.5:
                center_x = int(detection[0] * width)
                center_y = int(detection[1] * height)
                w = int(detection[2] * width)
                h = int(detection[3] * height)

                x = int(center_x - w / 2)
                y = int(center_y - h / 2)

                boxes.append([x, y, w, h])
                confidences.append(float(confidence))
                class_ids.append(class_id)

    # 非极大值抑制
    indexes = cv2.dnn.NMSBoxes(boxes, confidences, 0.5, 0.4)

    # 绘制检测结果
    font = cv2.FONT_HERSHEY_PLAIN
    colors = np.random.uniform(0, 255, size=(len(classes), 3))

    if len(indexes) > 0:
        for i in indexes.flatten():
            x, y, w, h = boxes[i]
            label = str(classes[class_ids[i]])
            confidence = str(round(confidences[i], 2))
            color = colors[class_ids[i]]
            cv2.rectangle(frame, (x, y), (x + w, y + h), color, 2)
            cv2.putText(frame, label + " " + confidence, (x, y + 20), font, 2, color, 2)

    # 显示帧
    cv2.imshow('YOLO Object Detection', frame)

    if cv2.waitKey(1) & 0xFF == ord('q'):
        break

# 释放摄像头并关闭所有窗口
cap.release()
cv2.destroyAllWindows()
步骤操作说明
1加载模型和类别用 cv2.dnn.readNet() 加载模型配置和权重文件,读取类别名称文件
2读取视频帧同 Haar 级联分类器
3准备输入图像使用 cv2.dnn.blobFromImage() 对图像进行预处理
4前向传播调用 net.forward() 进行推理,得到输出结果
5处理输出结果筛选出置信度高于阈值的检测结果,记录矩形框、置信度和类别信息
6非极大值抑制使用 cv2.dnn.NMSBoxes() 去除重叠的检测框
7绘制检测结果在图像上绘制矩形框和类别标签

五、实时目标跟踪

5.1 KCF(Kernelized Correlation Filters)跟踪器

import cv2

# 打开摄像头
cap = cv2.VideoCapture(0)

# 读取第一帧
ret, frame = cap.read()

# 选择跟踪区域
bbox = cv2.selectROI(frame, False)

# 创建 KCF 跟踪器
tracker = cv2.TrackerKCF_create()

# 初始化跟踪器
tracker.init(frame, bbox)

while True:
    ret, frame = cap.read()

    if not ret:
        break

    # 更新跟踪器
    success, bbox = tracker.update(frame)

    # 绘制跟踪结果
    if success:
        (x, y, w, h) = [int(v) for v in bbox]
        cv2.rectangle(frame, (x, y), (x + w, y + h), (0, 255, 0), 2)
    else:
        cv2.putText(frame, "Tracking failed", (100, 80), cv2.FONT_HERSHEY_SIMPLEX, 0.75, (0, 0, 255), 2)

    # 显示帧
    cv2.imshow('KCF Tracking', frame)

    if cv2.waitKey(1) & 0xFF == ord('q'):
        break

# 释放摄像头并关闭所有窗口
cap.release()
cv2.destroyAllWindows()
步骤操作说明
1打开摄像头并读取第一帧同前面视频处理操作
2选择跟踪区域使用 cv2.selectROI() 让用户手动选择要跟踪的目标区域
3创建并初始化跟踪器使用 cv2.TrackerKCF_create() 创建 KCF 跟踪器,并使用第一帧和选择的区域进行初始化
4跟踪目标在后续帧中调用 tracker.update() 更新跟踪器状态,获取新的跟踪区域
5绘制跟踪结果根据跟踪结果在图像上绘制矩形框或显示跟踪失败信息

六、实时图像处理

6.1 图像滤波

import cv2
import numpy as np

# 打开摄像头
cap = cv2.VideoCapture(0)

while True:
    ret, frame = cap.read()

    if not ret:
        break

    # 均值滤波
    blurred = cv2.blur(frame, (5, 5))

    # 高斯滤波
    gaussian_blurred = cv2.GaussianBlur(frame, (5, 5), 0)

    # 显示原始图像和滤波后的图像
    cv2.imshow('Original', frame)
    cv2.imshow('Blurred', blurred)
    cv2.imshow('Gaussian Blurred', gaussian_blurred)

    if cv2.waitKey(1) & 0xFF == ord('q'):
        break

# 释放摄像头并关闭所有窗口
cap.release()
cv2.destroyAllWindows()
滤波类型函数作用参数说明
均值滤波cv2.blur()平滑图像,去除噪声第一个参数为输入图像,第二个参数为滤波核大小
高斯滤波cv2.GaussianBlur()更有效地去除高斯噪声第一个参数为输入图像,第二个参数为滤波核大小,第三个参数为高斯核标准差

6.2 边缘检测

import cv2

# 打开摄像头
cap = cv2.VideoCapture(0)

while True:
    ret, frame = cap.read()

    if not ret:
        break

    # 转换为灰度图像
    gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)

    # Canny 边缘检测
    edges = cv2.Canny(gray, 100, 200)

    # 显示原始图像和边缘检测结果
    cv2.imshow('Original', frame)
    cv2.imshow('Edges', edges)

    if cv2.waitKey(1) & 0xFF == ord('q'):
        break

# 释放摄像头并关闭所有窗口
cap.release()
cv2.destroyAllWindows()
步骤操作说明
1读取视频帧同前面视频处理操作
2转换为灰度图像减少计算量,便于边缘检测
3边缘检测使用 cv2.Canny() 进行边缘检测,两个阈值参数用于控制边缘的检测灵敏度
4显示结果显示原始图像和边缘检测后的图像

七、实时应用案例

7.1 智能安防监控系统

import cv2
import time

# 加载人脸分类器
face_cascade = cv2.CascadeClassifier(cv2.data.haarcascades + 'haarcascade_frontalface_default.xml')

# 打开摄像头
cap = cv2.VideoCapture(0)

# 初始化视频写入器
fourcc = cv2.VideoWriter_fourcc(*'XVID')
out = None

while True:
    ret, frame = cap.read()

    if not ret:
        break

    # 转换为灰度图像
    gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)

    # 检测人脸
    faces = face_cascade.detectMultiScale(gray, 1.1, 4)

    if len(faces) > 0:
        if out is None:
            # 开始录制视频
            out = cv2.VideoWriter('alert_video.avi', fourcc, 20.0, (frame.shape[1], frame.shape[0]))
            start_time = time.time()

        # 在检测到的人脸周围绘制矩形
        for (x, y, w, h) in faces:
            cv2.rectangle(frame, (x, y), (x + w, y + h), (255, 0, 0), 2)

        # 写入视频帧
        out.write(frame)

        # 录制时间超过 10 秒,停止录制
        if time.time() - start_time > 10:
            out.release()
            out = None
    else:
        if out is not None:
            out.release()
            out = None

    # 显示帧
    cv2.imshow('Smart Surveillance', frame)

    if cv2.waitKey(1) & 0xFF == ord('q'):
        break

# 释放摄像头并关闭所有窗口
cap.release()
if out is not None:
    out.release()
cv2.destroyAllWindows()
步骤操作说明
1加载分类器和打开摄像头同 Haar 级联分类器部分
2初始化视频写入器使用 cv2.VideoWriter_fourcc() 和 cv2.VideoWriter() 初始化视频写入器
3检测人脸利用 Haar 级联分类器检测人脸
4录制视频当检测到人脸时开始录制视频,录制时间超过 10 秒停止录制
5显示帧实时显示视频帧

7.2 手势识别系统

import cv2
import numpy as np

# 打开摄像头
cap = cv2.VideoCapture(0)

while True:
    ret, frame = cap.read()

    if not ret:
        break

    # 定义手势区域
    roi = frame[100:300, 100:300]

    # 转换为灰度图像
    gray = cv2.cvtColor(roi, cv2.COLOR_BGR2GRAY)

    # 高斯滤波
    blurred = cv2.GaussianBlur(gray, (5, 5), 0)

    # 阈值处理
    _, thresh = cv2.threshold(blurred, 127, 255, cv2.THRESH_BINARY_INV)

    # 查找轮廓
    contours, _ = cv2.findContours(thresh.copy(), cv2.RETR_TREE, cv2.CHAIN_APPROX_SIMPLE)

    if len(contours) > 0:
        # 找到最大的轮廓
        cnt = max(contours, key=cv2.contourArea)

        # 计算凸包
        hull = cv2.convexHull(cnt)

        # 绘制轮廓和凸包
        cv2.drawContours(roi, [cnt], 0, (0, 255, 0), 2)
        cv2.drawContours(roi, [hull], 0, (0, 0, 255), 2)

        # 计算凸包缺陷
        hull = cv2.convexHull(cnt, returnPoints=False)
        defects = cv2.convexityDefects(cnt, hull)

        if defects is not None:
            count_defects = 0

            for i in range(defects.shape[0]):
                s, e, f, d = defects[i, 0]
                start = tuple(cnt[s][0])
                end = tuple(cnt[e][0])
                far = tuple(cnt[f][0])

                # 计算三角形的边长
                a = np.sqrt((end[0] - start[0]) ** 2 + (end[1] - start[1]) ** 2)
                b = np.sqrt((far[0] - start[0]) ** 2 + (far[1] - start[1]) ** 2)
                c = np.sqrt((end[0] - far[0]) ** 2 + (end[1] - far[1]) ** 2)

                # 计算角度
                angle = np.arccos((b ** 2 + c ** 2 - a ** 2) / (2 * b * c)) * 180 / np.pi

                if angle <= 90:
                    count_defects += 1
                    cv2.circle(roi, far, 5, (0, 0, 255), -1)

            # 根据缺陷数量判断手势
            if count_defects == 0:
                cv2.putText(frame, "Closed Fist", (50, 50), cv2.FONT_HERSHEY_SIMPLEX, 1, (0, 255, 0), 2)
            elif count_defects == 1:
                cv2.putText(frame, "One Finger", (50, 50), cv2.FONT_HERSHEY_SIMPLEX, 1, (0, 255, 0), 2)
            elif count_defects == 2:
                cv2.putText(frame, "Two Fingers", (50, 50), cv2.FONT_HERSHEY_SIMPLEX, 1, (0, 255, 0), 2)
            elif count_defects == 3:
                cv2.putText(frame, "Three Fingers", (50, 50), cv2.FONT_HERSHEY_SIMPLEX, 1, (0, 255, 0), 2)
            elif count_defects == 4:
                cv2.putText(frame, "Four Fingers", (50, 50), cv2.FONT_HERSHEY_SIMPLEX, 1, (0, 255, 0), 2)
            else:
                cv2.putText(frame, "Open Hand", (50, 50), cv2.FONT_HERSHEY_SIMPLEX, 1, (0, 255, 0), 2)

    # 显示帧
    cv2.imshow('Gesture Recognition', frame)

    if cv2.waitKey(1) & 0xFF == ord('q'):
        break

# 释放摄像头并关闭所有窗口
cap.release()
cv2.destroyAllWindows()
步骤操作说明
1打开摄像头并读取帧同前面视频处理操作
2定义手势区域从视频帧中选取特定区域进行手势识别
3图像预处理转换为灰度图像、高斯滤波、阈值处理
4查找轮廓和凸包使用 cv2.findContours() 查找轮廓,cv2.convexHull() 计算凸包
5计算凸包缺陷通过 cv2.convexityDefects() 计算凸包缺陷,根据缺陷数量判断手势
6显示结果在图像上显示识别出的手势信息

八、小结

OpenCV 在实时应用开发中具有强大的功能和广泛的应用场景。通过本文介绍的环境搭建、基本操作、目标检测、跟踪、图像处理以及应用案例等内容,开发者可以利用 OpenCV 快速实现各种实时应用。在实际开发中,可根据具体需求选择合适的算法和技术,并不断优化以提高应用性能。

http://www.dtcms.com/a/108999.html

相关文章:

  • 操作系统(一):概念及主流系统全分析
  • 大模型学习三:DeepSeek R1蒸馏模型组ollama调用流程
  • Vue2 生命周期
  • Adam vs SGD vs RMSProp:PyTorch优化器选择
  • 美关税加征下,Odoo免费开源ERP如何助企业破局?
  • 【无标题 langsmith
  • DNS域名解析过程 + 安全 / 性能优化方向
  • 在线下载国内外各种常见视频网站视频的网页端工具
  • frp 让服务器远程调用本地的服务(比如你的java 8080项目)
  • AIGC7——AIGC驱动的视听内容定制化革命:从Sora到商业化落地
  • S3C2410 的总线架构
  • OpenCV 图形API(11)对图像进行掩码操作的函数mask()
  • RK3568 gpio模拟i2c 配置hym8563 RTC时钟
  • 19c21c单机/RAC手工清理标准化文档
  • 中小企业数字化转型的本质:在Websoft9应用平台上实现开源工具与商业软件的统一
  • GitHub 趋势日报 (2025年04月02日)
  • 《深入理解Java虚拟机:JVM高级特性与最佳实践(第3版)》第2章 Java内存区域与内存溢出异常
  • springboot 启动方式 装配流程 自定义starter 文件加载顺序 常见设计模式
  • 【PHP】PHP网站常见一些安全漏洞及防御方法
  • DM数据库配置归档模式的两种方式
  • NOA是什么?国内自动驾驶技术的现状是怎么样的?
  • 清晰易懂的 Flutter 卸载和清理教程
  • 漫威蜘蛛侠2(Marvel‘s Spider-Man 2)
  • 算法复杂度:从理论到实战的全面解析
  • 电脑文件怎么压缩打包发送?
  • AI大模型重构医药流通供应链:传统IT顾问的转型指南
  • 可灵视频+Runway 双引擎:企业短视频营销 AI 化解决方案
  • Kali Linux 2025.1a:主题焕新与树莓派支持的深度解析
  • 训练出一个模型需要哪些步骤
  • lua表table和JSON字符串互转