关于#python#的问题:基于Spyder环境下的Python,使用OpenCV进行静态和动态目标(小型无人机)的识别,并对动态目标进行跟踪

基于Spyder环境下的Python,使用OpenCV进行静态和动态目标(小型无人机)的识别,并对动态目标进行跟踪。
识别特征为颜色和轮廓。
需要流程图和每一步代码的作用。

该回答引用ChatGPT

以下是基于Spyder环境下的Python,使用OpenCV进行静态和动态目标(小型无人机)的识别,并对动态目标进行跟踪的流程图和每一步代码的作用:

流程图

img

实现代码

# 导入OpenCV库
import cv2

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

# 预处理
gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
blur = cv2.GaussianBlur(gray, (5, 5), 0)

# 颜色阈值分割
thresh = cv2.inRange(blur, (0, 0, 0), (50, 50, 50))

# 形态学操作
kernel = cv2.getStructuringElement(cv2.MORPH_RECT, (5, 5))
closed = cv2.morphologyEx(thresh, cv2.MORPH_CLOSE, kernel)
opened = cv2.morphologyEx(closed, cv2.MORPH_OPEN, kernel)

# 轮廓检测
contours, hierarchy = cv2.findContours(opened, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)

# 筛选目标
for cnt in contours:
    area = cv2.contourArea(cnt)
    if area < 100:
        continue
    x, y, w, h = cv2.boundingRect(cnt)
    cv2.rectangle(image, (x, y), (x+w, y+h), (0, 0, 255), 2)

# 目标跟踪
tracker = cv2.TrackerKCF_create()
bbox = cv2.selectROI(image, False)
ok = tracker.init(image, bbox)

while True:
    ret, image = cap.read()
    if not ret:
        break
    ok, bbox = tracker.update(image)
    if ok:
        p1 = (int(bbox[0]), int(bbox[1]))
        p2 = (int(bbox[0] + bbox[2]), int(bbox[1] + bbox[3]))
        cv2.rectangle(image, p1, p2, (0, 255, 0), 2, 1)
    else:
        cv2.putText(image, "Tracking failure detected", (100, 80), cv2.FONT_HERSHEY_SIMPLEX, 0.75,(0,0,255),2)
    
    cv2.imshow("Tracking", image)
    if cv2.waitKey(1) & 0xFF == ord('q'):
        break

cv2.destroyAllWindows()


代码解释
1、导入OpenCV库:

import cv2

2、读取图像:

image = cv2.imread('image.jpg')

3、预处理:


gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
blur = cv2.GaussianBlur(gray, (5, 5), 0)

4、颜色阈值分

thresh = cv2.inRange(blur, (0, 0, 0), (50, 50, 50))

该步骤将图像转换为灰度图像,应用高斯滤波器对图像进行平滑处理,并将图像二值化为黑白图像,使得轮廓更加清晰。

5、形态学操作:


kernel = cv2.getStructuringElement(cv2.MORPH_RECT, (5, 5))
closed = cv2.morphologyEx(thresh, cv2.MORPH_CLOSE, kernel)
opened = cv2.morphologyEx(closed, cv2.MORPH_OPEN, kernel)

该步骤应用形态学操作来进一步去除图像噪声和孤立的像素点,使得目标区域更加连续。

6、轮廓检测:

contours, hierarchy = cv2.findContours(opened, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)

该步骤使用findContours函数来寻找图像中的所有轮廓,并返回所有轮廓的坐标和层次结构。

7、筛选目标:


for cnt in contours:
    area = cv2.contourArea(cnt)
    if area < 100:
        continue
    x, y, w, h = cv2.boundingRect(cnt)
    cv2.rectangle(image, (x, y), (x+w, y+h), (0, 0, 255), 2)

该步骤对所有检测到的轮廓进行遍历,计算每个轮廓的面积,如果面积小于100,则认为该轮廓不是目标。否则,使用boundingRect函数找到包含轮廓的最小矩形,并在图像中绘制该矩形。

8、目标跟踪:


tracker = cv2.TrackerKCF_create()
bbox = cv2.selectROI(image, False)
ok = tracker.init(image, bbox)

while True:
    ret, image = cap.read()
    if not ret:
        break
    ok, bbox = tracker.update(image)
    if ok:
        p1 = (int(bbox[0]), int(bbox[1]))
        p2 = (int(bbox[0] + bbox[2]), int(bbox[1] + bbox[3]))
        cv2.rectangle(image, p1, p2, (0, 255, 0), 2, 1)
    else:
        cv2.putText(image, "Tracking failure detected", (100, 80), cv2.FONT_HERSHEY_SIMPLEX, 0.75,(0,0,255),2)

    cv2.imshow("Tracking", image)
    if cv2.waitKey(1) & 0xFF == ord('q'):
        break

cv2.destroyAllWindows()

该步骤使用OpenCV内置的TrackerKCF算法对目标进行跟踪。首先,使用selectROI函数手动选择目标区域,然后使用init函数初始化跟踪器,并将其应用于图像序列中的每一帧。如果跟踪成功,则使用矩形框标记目标位置。如果跟踪失败,则在图像中显示警告信息。程序通过按下“q”键退出。

以上是基于Spyder环境下的Python,使用OpenCV进行静态和动态目标(小型无人机)的识别,并对动态目标进行跟踪的完整流程和代码实现,其中包括图像预处理、颜色阈值分割、形态学操作、轮廓检测、目标筛选和跟踪等步骤。

参考GPT和自己的思路,以下是基于Spyder环境下的Python,使用OpenCV进行静态和动态目标(小型无人机)的识别,并对动态目标进行跟踪的示例代码及相应解释:

流程图如下:

1. 读取视频帧
2. 将视频帧转换为HSV颜色空间
3. 根据预设的颜色范围提取目标颜色区域
4. 对目标颜色区域进行形态学操作,以去除噪声
5. 找出目标区域的轮廓
6. 对轮廓进行筛选,以排除非目标的干扰轮廓
7. 计算目标的质心位置
8. 将目标的质心位置与前一帧的位置进行比较,以确定目标是否移动
9. 如果目标移动,则对目标进行跟踪,并在跟踪框中标记目标位置;如果目标未移动,则继续检测下一帧

具体代码及解释如下:

import cv2
import numpy as np

# 定义颜色范围(HSV颜色空间)
lower_color = np.array([0, 100, 100]) # 颜色下限
upper_color = np.array([10, 255, 255]) # 颜色上限

# 创建结构元素,用于形态学操作
kernel = cv2.getStructuringElement(cv2.MORPH_RECT, (5,5))

# 创建追踪器,用于跟踪目标
tracker = cv2.TrackerKCF_create()

# 打开视频文件
cap = cv2.VideoCapture('drone.mp4')

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

# 将第一帧转换为HSV颜色空间
hsv = cv2.cvtColor(frame, cv2.COLOR_BGR2HSV)

# 创建输出窗口
cv2.namedWindow('output', cv2.WINDOW_NORMAL)

# 定义前一帧中目标的位置
prev_center = None

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

    # 将视频帧转换为HSV颜色空间
    hsv = cv2.cvtColor(frame, cv2.COLOR_BGR2HSV)

    # 提取目标颜色区域
    mask = cv2.inRange(hsv, lower_color, upper_color)

    # 进行形态学操作,去除噪声
    mask = cv2.morphologyEx(mask, cv2.MORPH_OPEN, kernel)

    # 查找目标轮廓
    contours, hierarchy = cv2.findContours(mask, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)

    # 筛选轮廓,排除非目标干扰
    center = None
    for cnt in contours:
        area = cv2.contourArea(cnt)
        if area < 100:
            continue
        # 计算轮廓的外接圆
       
(x, y), radius = cv2.minEnclosingCircle(cnt)
    # 计算轮廓的质心
    M = cv2.moments(cnt)
    cx = int(M['m10'] / M['m00'])
    cy = int(M['m01'] / M['m00'])
    center = (cx, cy)
    
    # 比较目标位置与前一帧的位置,判断目标是否移动
    if prev_center is not None:
        dx = abs(center[0] - prev_center[0])
        dy = abs(center[1] - prev_center[1])
        if dx < 5 and dy < 5:
            # 目标未移动,继续检测下一帧
            continue
    
    # 目标移动,进行跟踪
    tracker.init(frame, (x, y, radius, radius))
    
    # 记录当前帧中目标的位置
    prev_center = center
    
# 更新跟踪器
ret, bbox = tracker.update(frame)
if ret:
    # 跟踪成功,绘制跟踪框和质心位置
    x, y, w, h = [int(i) for i in bbox]
    cv2.rectangle(frame, (x,y), (x+w,y+h), (0,255,0), 2)
    cv2.circle(frame, center, 3, (0,0,255), -1)
else:
    # 跟踪失败,清空前一帧中目标的位置
    prev_center = None

# 显示输出窗口
cv2.imshow('output', frame)
key = cv2.waitKey(1)
if key == ord('q'):
    break
释放视频文件和输出窗口
cap.release()
cv2.destroyAllWindows()

解释:

  • 通过调用cv2.findContours()函数找到目标轮廓,并使用cv2.contourArea()函数计算轮廓面积。通过判断面积大小,筛选出面积大于100的目标轮廓。
  • 对于每个目标轮廓,计算其外接圆和质心,并将质心位置记录为当前帧中目标的位置。
  • 通过比较当前帧中目标的位置与前一帧中的位置,判断目标是否移动。如果目标未移动,则继续检测下一帧;如果目标移动,则使用cv2.TrackerKCF_create()函数创建追踪器,并使用tracker.init()函数对目标进行跟踪。
  • 使用tracker.update()函数更新跟踪器,并根据返回值判断跟踪是否成功。如果跟踪成功,则使用cv2.rectangle()函数在目标周围绘制跟踪框,并使用cv2.circle()函数绘制目标的质心位置;如果跟踪失败,则清空前一帧中目标的位置。
  • 使用cv2.imshow()函数显示输出窗口,并通过cv2.waitKey()函数等待用户输入,以实现按键退出程序的功能。

以下是可能的实现步骤和代码示例,

1.导入所需的库和模块

import cv2
import numpy as np

2.读取视频或图像

# 读取视频
cap = cv2.VideoCapture('video.mp4')

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

3.设定颜色范围,将图像转换为HSV色彩空间,并使用颜色过滤器进行目标筛选

# 设定颜色范围,这里以红色为例
lower_red = np.array([0, 50, 50])
upper_red = np.array([10, 255, 255])
lower_red2 = np.array([170, 50, 50])
upper_red2 = np.array([180, 255, 255])

# 将图像转换为HSV色彩空间
hsv = cv2.cvtColor(frame, cv2.COLOR_BGR2HSV)

# 使用颜色过滤器进行目标筛选
mask1 = cv2.inRange(hsv, lower_red, upper_red)
mask2 = cv2.inRange(hsv, lower_red2, upper_red2)
mask = mask1 + mask2

4.对图像进行二值化处理

ret, binary = cv2.threshold(gray, 127, 255, cv2.THRESH_BINARY)

5.对图像进行边缘检测

edges = cv2.Canny(binary, 100, 200)

6.对边缘图像进行轮廓检测,并绘制轮廓

contours, hierarchy = cv2.findContours(edges, cv2.RETR_TREE, cv2.CHAIN_APPROX_SIMPLE)
cv2.drawContours(frame, contours, -1, (0, 255, 0), 2)

7.对目标进行跟踪

# 定义追踪器
tracker = cv2.TrackerKCF_create()

# 选择目标
bbox = cv2.selectROI(frame, False)

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

# 开始跟踪
success, bbox = tracker.update(frame)

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

8.将处理后的图像显示出来

cv2.imshow('frame', frame)
cv2.waitKey(1)

以上是简单的实现步骤和示例代码,实际应用中可能还需要根据具体情况进行调整和优化

首先,我们需要安装OpenCV库。可以通过以下命令在终端中安装:

plaintext
Copy code
pip install opencv-python

接下来,我们来看一下实现的流程:

导入所需库


python
Copy code
import cv2
import numpy as np

读取视频或图像

python
Copy code
cap = cv2.VideoCapture('video.mp4') # 读取视频
# 或者读取图像
img = cv2.imread('image.jpg')

颜色识别

python
Copy code
# 将图片从RGB空间转换到HSV空间
hsv = cv2.cvtColor(img, cv2.COLOR_BGR2HSV)
# 设定颜色范围
lower_red = np.array([0, 50, 50])
upper_red = np.array([10, 255, 255])
# 根据颜色范围进行二值化处理
mask = cv2.inRange(hsv, lower_red, upper_red)
# 对二值化后的图像进行腐蚀和膨胀处理,以去除噪点
kernel = np.ones((5, 5), np.uint8)
mask = cv2.erode(mask, kernel, iterations=1)
mask = cv2.dilate(mask, kernel, iterations=1)
# 找到颜色区域的轮廓
contours, hierarchy = cv2.findContours(mask, cv2.RETR_TREE, cv2.CHAIN_APPROX_SIMPLE)
# 绘制轮廓
cv2.drawContours(img, contours, -1, (0, 255, 0), 2)



轮廓识别

python
Copy code
# 将图片转换为灰度图像
gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
# 对灰度图像进行二值化处理,以得到二值化后的图像
ret, thresh = cv2.threshold(gray, 127, 255, 0)
# 找到图像中的轮廓
contours, hierarchy = cv2.findContours(thresh, cv2.RETR_TREE, cv2.CHAIN_APPROX_SIMPLE)
# 绘制轮廓
cv2.drawContours(img, contours, -1, (0, 255, 0), 2)


目标跟踪

python
Copy code
# 定义跟踪器类型
tracker_type = 'BOOSTING'
# 创建跟踪器对象
if tracker_type == 'BOOSTING':
    tracker = cv2.TrackerBoosting_create()
elif tracker_type == 'MIL':
    tracker = cv2.TrackerMIL_create()
elif tracker_type == 'KCF':
    tracker = cv2.TrackerKCF_create()
elif tracker_type == 'TLD':
    tracker = cv2.TrackerTLD_create()
elif tracker_type == 'MEDIANFLOW':
    tracker = cv2.TrackerMedianFlow_create()
elif tracker_type == 'GOTURN':
    tracker = cv2.TrackerGOTURN_create()
elif tracker_type == 'MOSSE':
    tracker = cv2.TrackerMOSSE_create()
elif tracker_type == 'CSRT':
    tracker = cv2.TrackerCSRT_create()
# 选择要跟踪的目标
bbox = cv2.selectROI(img, False)
# 初始化跟踪器
tracker.init(img, bbox)
# 循环遍历视频的每一帧
while True:
    # 读取视频的下一帧
    ret, frame = cap.read()
    # 如果没有读取到帧,结束循环
    if not ret:
        break
    # 跟踪目标
    success, bbox = tracker.update(frame)
    # 如果跟踪成功,绘制跟踪框
    if success:
        x, y, w, h = [int(i) for i in bbox]
        cv2.rectangle(frame, (x, y), (x + w, y + h), (255, 0, 0), 2)
    # 显示视频帧
    cv2.imshow('frame', frame)
    # 如果按下q键,结束循环
    if cv2.waitKey(1) & 0xFF == ord('q'):
        break
# 释放资源
cap.release()
cv2.destroyAllWindows()


上述代码中,我们使用了cv2.Tracker模块和不同的跟踪器类型,以实现对动态目标的跟踪。
最后,我们可以将上述代码整合起来,得到完整的代码实现静态和动态目标(小型无人机)的识别,并对动态目标进行跟踪:

import cv2
import numpy as np

定义跟踪器类型

tracker_type = 'BOOSTING'

创建跟踪器对象
if tracker_type == 'BOOSTING':
    tracker = cv2.TrackerBoosting_create()
elif tracker_type == 'MIL':
    tracker = cv2.TrackerMIL_create()
elif tracker_type == 'KCF':
    tracker = cv2.TrackerKCF_create()
elif tracker_type == 'TLD':
    tracker = cv2.TrackerTLD_create()
elif tracker_type == 'MEDIANFLOW':
    tracker = cv2.TrackerMedianFlow_create()
elif tracker_type == 'GOTURN':
    tracker = cv2.TrackerGOTURN_create()
elif tracker_type == 'MOSSE':
    tracker = cv2.TrackerMOSSE_create()
elif tracker_type == 'CSRT':
    tracker = cv2.TrackerCSRT_create()

读取视频或图像

cap = cv2.VideoCapture('video.mp4') # 读取视频
img = cv2.imread('image.jpg') # 读取图像

颜色识别
将图片从RGB空间转换到HSV空间
hsv = cv2.cvtColor(img, cv2.COLOR_BGR2HSV)

设定颜色范围
lower_red = np.array([0, 50, 50])
upper_red = np.array([10, 255, 255])

```

根据颜色范围进行二值化处理

以下答案由GPT-3.5大模型与博主波罗歌共同编写:
这是一个比较复杂的问题,需要分步骤进行解答。

  1. 安装OpenCV

首先需要安装OpenCV,可以通过pip install opencv-python来安装。

pip install opencv-python
  1. 导入模块

接下来需要导入OpenCV模块,以及其他需要用到的模块。

import cv2
import numpy as np
  1. 读取视频

使用OpenCV读取视频文件,得到视频的每一帧图像。

cap = cv2.VideoCapture('video.mp4')
while(cap.isOpened()):
    ret, frame = cap.read()
    if ret==True:
        # 处理每一帧图像
    else:
        break
cap.release()
cv2.destroyAllWindows()
  1. 检测颜色

对每一帧图像进行颜色检测,得到满足特定颜色条件的像素点。

# 定义颜色区间
lower = np.array([0, 100, 100])
upper = np.array([10, 255, 255])

# 转换颜色空间
hsv = cv2.cvtColor(frame, cv2.COLOR_BGR2HSV)

# 创建掩膜
mask = cv2.inRange(hsv, lower, upper)

# 根据掩膜提取像素点
output = cv2.bitwise_and(frame, frame, mask= mask)
  1. 轮廓检测

对满足颜色条件的像素点进行轮廓检测,得到目标物体的边界。

# 寻找轮廓
contours, hierarchy = cv2.findContours(mask, cv2.RETR_TREE, cv2.CHAIN_APPROX_SIMPLE)

# 计算轮廓面积
contour_area = []

for i in contours:
    contour_area.append(cv2.contourArea(i))
    
max_area = max(contour_area)

# 找到最大轮廓
for i in contours:
    if cv2.contourArea(i) == max_area:
        max_contour = i

# 绘制轮廓
cv2.drawContours(frame, [max_contour], 0, (255, 0, 0), 2)
  1. 跟踪目标

使用一定的跟踪算法,对目标物体进行跟踪。

# 定义跟踪器
tracker = cv2.TrackerKCF_create()

# 定义跟踪区域
bbox = cv2.boundingRect(max_contour)

# 将跟踪器应用于目标物体
ok = tracker.init(frame, bbox)

# 跟踪目标
ok, bbox = tracker.update(frame)

# 绘制跟踪框架
if ok:
    p1 = (int(bbox[0]), int(bbox[1]))
    p2 = (int(bbox[0] + bbox[2]), int(bbox[1] + bbox[3]))
    cv2.rectangle(frame, p1, p2, (0,255,0), 2, 1)
else:
    cv2.putText(frame, "Unable to detect object", (100,80), cv2.FONT_HERSHEY_SIMPLEX, 0.75,(0,0,255),2)
  1. 完整代码
import cv2
import numpy as np

cap = cv2.VideoCapture('video.mp4')
while(cap.isOpened()):
    ret, frame = cap.read()
    if ret==True:
        # 定义颜色区间
        lower = np.array([0, 100, 100])
        upper = np.array([10, 255, 255])

        # 转换颜色空间
        hsv = cv2.cvtColor(frame, cv2.COLOR_BGR2HSV)

        # 创建掩膜
        mask = cv2.inRange(hsv, lower, upper)

        # 根据掩膜提取像素点
        output = cv2.bitwise_and(frame, frame, mask= mask)

        # 寻找轮廓
        contours, hierarchy = cv2.findContours(mask, cv2.RETR_TREE, cv2.CHAIN_APPROX_SIMPLE)

        # 计算轮廓面积
        contour_area = []

        for i in contours:
            contour_area.append(cv2.contourArea(i))

        max_area = max(contour_area)

        # 找到最大轮廓
        for i in contours:
            if cv2.contourArea(i) == max_area:
                max_contour = i

        # 绘制轮廓
        cv2.drawContours(frame, [max_contour], 0, (255, 0, 0), 2)

        # 定义跟踪器
        tracker = cv2.TrackerKCF_create()

        # 定义跟踪区域
        bbox = cv2.boundingRect(max_contour)

        # 将跟踪器应用于目标物体
        ok = tracker.init(frame, bbox)

        # 跟踪目标
        ok, bbox = tracker.update(frame)

        # 绘制跟踪框架
        if ok:
            p1 = (int(bbox[0]), int(bbox[1]))
            p2 = (int(bbox[0] + bbox[2]), int(bbox[1] + bbox[3]))
            cv2.rectangle(frame, p1, p2, (0,255,0), 2, 1)
        else:
            cv2.putText(frame, "Unable to detect object", (100,80), cv2.FONT_HERSHEY_SIMPLEX, 0.75,(0,0,255),2)

        # 显示处理结果
        cv2.imshow('frame',frame)
        if cv2.waitKey(25) & 0xFF == ord('q'):
            break
    else:
        break
cap.release()
cv2.destroyAllWindows()

这是一个大致的流程图,但是在实际操作中,需要根据具体需求进行调整和优化。

image.png


如果我的回答解决了您的问题,请采纳!