Mac 电脑配置yolov8运行环境实现目标追踪、计数、画出轨迹、多线程-LMLPHP

📙 Mac 电脑 配置 yolov8 环境

  • YOLO 推理测试、小数据集训练,基础版 Mac 即可满足
  • 博主这里代码运行的 Mac 版本为 M1 Pro

conda create -n yolopy39 python=3.9
conda activate yolopy39

pip3 install torch torchvision torchaudio

# ultralytics 对 opencv-python 的版本需求如下
pip3 install opencv-python>=4.6.0
# 因此我选择安装的版本如下
pip3 install opencv-python==4.6.0.66

cd Desktop

mkdir moli

cd moli

git clone https://github.com/ultralytics/ultralytics.git
pip install -e .

pwd             
/Users/moli/Desktop/moli/ultralytics


📙 代码运行

推理测试
yolo predict model=yolov8n.pt source='https://ultralytics.com/images/bus.jpg'
# 输出如下
Matplotlib is building the font cache; this may take a moment.
Downloading https://github.com/ultralytics/assets/releases/download/v8.2.0/yolov8n.pt to 'yolov8n.pt'...
100%|███████████████████████████████████████████████████████████████████████████████████████████████████████████████████████████| 6.25M/6.25M [01:34<00:00, 69.6kB/s]
Ultralytics YOLOv8.2.77 🚀 Python-3.9.19 torch-2.2.2 CPU (Apple M1 Pro)
[W NNPACK.cpp:64] Could not initialize NNPACK! Reason: Unsupported hardware.
YOLOv8n summary (fused): 168 layers, 3,151,904 parameters, 0 gradients, 8.7 GFLOPs

Downloading https://ultralytics.com/images/bus.jpg to 'bus.jpg'...
100%|██████████████████████████████████████████████████████████████████████████████████████████████████████████████████████████████| 134k/134k [00:00<00:00, 470kB/s]
image 1/1 /Users/moli/Desktop/moli/ultralytics/bus.jpg: 640x480 4 persons, 1 bus, 1 stop sign, 221.3ms
Speed: 5.8ms preprocess, 221.3ms inference, 4.0ms postprocess per image at shape (1, 3, 640, 480)
Results saved to /Users/moli/Desktop/moli/ultralytics/runs/detect/predict

模型训练 - 转 onnx
from ultralytics import YOLO

# Load a model
model = YOLO("yolov8n.yaml")  # build a new model from scratch
model = YOLO("yolov8n.pt")  # load a pretrained model (recommended for training)

# Use the model
model.train(data="coco8.yaml", epochs=3)  # train the model
metrics = model.val()  # evaluate model performance on the validation set
results = model("https://ultralytics.com/images/bus.jpg")  # predict on an image

# 转换 onnx 也是封装好的模块,这里调用传参即可
path = model.export(format="onnx")  # export the model to ONNX format
python train_test.py 

[W NNPACK.cpp:64] Could not initialize NNPACK! Reason: Unsupported hardware.
Ultralytics YOLOv8.2.77 🚀 Python-3.9.19 torch-2.2.2 CPU (Apple M1 Pro)
engine/trainer: task=detect, mode=train, model=yolov8n.pt, data=coco8.yaml, epochs=3, time=None, patience=100, batch=16, imgsz=640, save=True, save_period=-1, cache=False, device=None, workers=8, project=None, name=train, exist_ok=False, pretrained=True, optimizer=auto, verbose=True, seed=0, deterministic=True, single_cls=False, rect=False, cos_lr=False, close_mosaic=10, resume=False, amp=True, fraction=1.0, profile=False, freeze=None, multi_scale=False, overlap_mask=True, mask_ratio=4, dropout=0.0, val=True, split=val, save_json=False, save_hybrid=False, conf=None, iou=0.7, max_det=300, half=False, dnn=False, plots=True, source=None, vid_stride=1, stream_buffer=False, visualize=False, augment=False, agnostic_nms=False, classes=None, retina_masks=False, embed=None, show=False, save_frames=False, save_txt=False, save_conf=False, save_crop=False, show_labels=True, show_conf=True, show_boxes=True, line_width=None, format=torchscript, keras=False, optimize=False, int8=False, dynamic=False, simplify=False, opset=None, workspace=4, nms=False, lr0=0.01, lrf=0.01, momentum=0.937, weight_decay=0.0005, warmup_epochs=3.0, warmup_momentum=0.8, warmup_bias_lr=0.1, box=7.5, cls=0.5, dfl=1.5, pose=12.0, kobj=1.0, label_smoothing=0.0, nbs=64, hsv_h=0.015, hsv_s=0.7, hsv_v=0.4, degrees=0.0, translate=0.1, scale=0.5, shear=0.0, perspective=0.0, flipud=0.0, fliplr=0.5, bgr=0.0, mosaic=1.0, mixup=0.0, copy_paste=0.0, auto_augment=randaugment, erasing=0.4, crop_fraction=1.0, cfg=None, tracker=botsort.yaml, save_dir=/Users/moli/Desktop/moli/ultralytics/runs/detect/train

Dataset 'coco8.yaml' images not found ⚠️, missing path '/Users/moli/Desktop/moli/datasets/coco8/images/val'
Downloading https://ultralytics.com/assets/coco8.zip to '/Users/moli/Desktop/moli/datasets/coco8.zip'...
100%|███████████████████████████████████████████████████████████████████████████████████████████| 433k/433k [00:03<00:00, 135kB/s]
Unzipping /Users/moli/Desktop/moli/datasets/coco8.zip to /Users/moli/Desktop/moli/datasets/coco8...: 100%|██████████| 25/25 [00:00
Dataset download success ✅ (5.4s), saved to /Users/moli/Desktop/moli/datasets


...
...

Logging results to /Users/moli/Desktop/moli/ultralytics/runs/detect/train
Starting training for 3 epochs...

      Epoch    GPU_mem   box_loss   cls_loss   dfl_loss  Instances       Size
        1/3         0G      1.412      2.815      1.755         22        640: 100%|██████████| 1/1 [00:01<00:00,  1.90s/it]
                 Class     Images  Instances      Box(P          R      mAP50  mAP50-95): 100%|██████████| 1/1 [00:00<00:00,  1.30
                   all          4         17      0.613      0.883      0.888      0.616

      Epoch    GPU_mem   box_loss   cls_loss   dfl_loss  Instances       Size
        2/3         0G      1.249      2.621      1.441         23        640: 100%|██████████| 1/1 [00:01<00:00,  1.51s/it]
                 Class     Images  Instances      Box(P          R      mAP50  mAP50-95): 100%|██████████| 1/1 [00:00<00:00,  2.24
                   all          4         17      0.598      0.896      0.888      0.618

      Epoch    GPU_mem   box_loss   cls_loss   dfl_loss  Instances       Size
        3/3         0G      1.142      4.221      1.495         16        640: 100%|██████████| 1/1 [00:01<00:00,  1.50s/it]
                 Class     Images  Instances      Box(P          R      mAP50  mAP50-95): 100%|██████████| 1/1 [00:00<00:00,  2.06
                   all          4         17       0.58      0.833      0.874      0.613

3 epochs completed in 0.002 hours.
Optimizer stripped from /Users/moli/Desktop/moli/ultralytics/runs/detect/train/weights/last.pt, 6.5MB
Optimizer stripped from /Users/moli/Desktop/moli/ultralytics/runs/detect/train/weights/best.pt, 6.5MB

Validating /Users/moli/Desktop/moli/ultralytics/runs/detect/train/weights/best.pt...
Ultralytics YOLOv8.2.77 🚀 Python-3.9.19 torch-2.2.2 CPU (Apple M1 Pro)
Model summary (fused): 168 layers, 3,151,904 parameters, 0 gradients, 8.7 GFLOPs
                 Class     Images  Instances      Box(P          R      mAP50  mAP50-95): 100%|██████████| 1/1 [00:00<00:00,  1.72
                   all          4         17      0.599      0.898      0.888      0.618
                person          3         10      0.647        0.5       0.52       0.29
                   dog          1          1      0.315          1      0.995      0.597
                 horse          1          2      0.689          1      0.995      0.598
              elephant          1          2      0.629      0.887      0.828      0.332
              umbrella          1          1      0.539          1      0.995      0.995
          potted plant          1          1      0.774          1      0.995      0.895
Speed: 4.2ms preprocess, 134.0ms inference, 0.0ms loss, 0.8ms postprocess per image
Results saved to /Users/moli/Desktop/moli/ultralytics/runs/detect/train
Ultralytics YOLOv8.2.77 🚀 Python-3.9.19 torch-2.2.2 CPU (Apple M1 Pro)
Model summary (fused): 168 layers, 3,151,904 parameters, 0 gradients, 8.7 GFLOPs
val: Scanning /Users/moli/Desktop/moli/datasets/coco8/labels/val.cache... 4 images, 0 backgrounds, 0 corrupt: 100%|██████████| 4/4
                 Class     Images  Instances      Box(P          R      mAP50  mAP50-95): 100%|██████████| 1/1 [00:00<00:00,  2.02
                   all          4         17      0.599      0.898      0.888      0.618
                person          3         10      0.647        0.5       0.52       0.29
                   dog          1          1      0.315          1      0.995      0.597
                 horse          1          2      0.689          1      0.995      0.598
              elephant          1          2      0.629      0.887      0.828      0.332
              umbrella          1          1      0.539          1      0.995      0.995
          potted plant          1          1      0.774          1      0.995      0.895
Speed: 4.1ms preprocess, 113.0ms inference, 0.0ms loss, 0.7ms postprocess per image
Results saved to /Users/moli/Desktop/moli/ultralytics/runs/detect/train2

image 1/1 /Users/moli/Desktop/moli/ultralytics/ultralytics/assets/bus.jpg: 640x480 4 persons, 1 bus, 188.4ms
Speed: 3.9ms preprocess, 188.4ms inference, 1.0ms postprocess per image at shape (1, 3, 640, 480)
Ultralytics YOLOv8.2.77 🚀 Python-3.9.19 torch-2.2.2 CPU (Apple M1 Pro)

# 开始模型转换

PyTorch: starting from '/Users/moli/Desktop/moli/ultralytics/runs/detect/train/weights/best.pt' with input shape (1, 3, 640, 640) BCHW and output shape(s) (1, 84, 8400) (6.2 MB)
requirements: Ultralytics requirement ['onnx>=1.12.0'] not found, attempting AutoUpdate...

Looking in indexes: http://pypi.douban.com/simple, http://mirrors.aliyun.com/pypi/simple/, https://pypi.tuna.tsinghua.edu.cn/simple/, http://pypi.mirrors.ustc.edu.cn/simple/
Collecting onnx>=1.12.0
  Downloading http://mirrors.ustc.edu.cn/pypi/packages/4e/35/abbf2fa3dbb96b430f6e810e3fb7bc042ed150f371cb1aedb47052c40f8e/onnx-1.16.2-cp39-cp39-macosx_11_0_universal2.whl (16.5 MB)
     ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━ 16.5/16.5 MB 11.4 MB/s eta 0:00:00
Requirement already satisfied: numpy>=1.20 in /Users/moli/opt/anaconda3/envs/yolopy39/lib/python3.9/site-packages (from onnx>=1.12.0) (1.26.4)
Collecting protobuf>=3.20.2 (from onnx>=1.12.0)
  Downloading http://mirrors.ustc.edu.cn/pypi/packages/ca/bc/bceb11aa96dd0b2ae7002d2f46870fbdef7649a0c28420f0abb831ee3294/protobuf-5.27.3-cp38-abi3-macosx_10_9_universal2.whl (412 kB)
Installing collected packages: protobuf, onnx
Successfully installed onnx-1.16.2 protobuf-5.27.3

requirements: AutoUpdate success ✅ 22.0s, installed 1 package: ['onnx>=1.12.0']
requirements: ⚠️ Restart runtime or rerun command for updates to take effect


ONNX: starting export with onnx 1.16.2 opset 17...
ONNX: export success ✅ 24.4s, saved as '/Users/moli/Desktop/moli/ultralytics/runs/detect/train/weights/best.onnx' (12.2 MB)

Export complete (26.1s)
Results saved to /Users/moli/Desktop/moli/ultralytics/runs/detect/train/weights
Predict:         yolo predict task=detect model=/Users/moli/Desktop/moli/ultralytics/runs/detect/train/weights/best.onnx imgsz=640  
Validate:        yolo val task=detect model=/Users/moli/Desktop/moli/ultralytics/runs/detect/train/weights/best.onnx imgsz=640 data=/Users/moli/Desktop/moli/ultralytics/ultralytics/cfg/datasets/coco8.yaml  
Visualize:       https://netron.app
ls runs/detect/train/       

F1_curve.png			R_curve.png			confusion_matrix_normalized.png	results.csv			train_batch1.jpg		val_batch0_pred.jpg
PR_curve.png			args.yaml			labels.jpg			results.png			train_batch2.jpg		weights
P_curve.png			confusion_matrix.png		labels_correlogram.jpg		train_batch0.jpg		val_batch0_labels.jpg

(yolopy39) moli@molideMacBook-Pro ultralytics % ls runs/detect/train/weights 
best.onnx	best.pt		last.pt

视频-目标检测
cat yolov8_1.py 
from ultralytics import YOLO

# Load an official or custom model
model = YOLO("yolov8n.pt")  # Load an official Detect model
#model = YOLO("yolov8n-seg.pt")  # Load an official Segment model
#model = YOLO("yolov8n-pose.pt")  # Load an official Pose model
#model = YOLO("path/to/best.pt")  # Load a custom trained model

# Perform tracking with the model
source = 'video/people.mp4'
results = model.track(source, show=True)  # Tracking with default tracker

Mac 电脑配置yolov8运行环境实现目标追踪、计数、画出轨迹、多线程-LMLPHP

调用 Mac 电脑摄像头
from ultralytics import YOLO

# Load an official or custom model
model = YOLO("yolov8n.pt")  # Load an official Detect model

#source = 'video/people.mp4'
source = 0
results = model.track(source, show=True)  # Tracking with default tracker

# results = model.track(source, show=True, tracker="bytetrack.yaml")  # with ByteTrack

Mac 电脑配置yolov8运行环境实现目标追踪、计数、画出轨迹、多线程-LMLPHP

PersistingTracksLoop 持续目标跟踪
                  
import cv2

from ultralytics import YOLO

# Load the YOLOv8 model
model = YOLO("yolov8n.pt")

# Open the video file
video_path = "./video/test_people.mp4"
cap = cv2.VideoCapture(video_path)

# Loop through the video frames
while cap.isOpened():
    # Read a frame from the video
    success, frame = cap.read()

    if success:
        # Run YOLOv8 tracking on the frame, persisting tracks between frames
        results = model.track(frame, persist=True)

        # Visualize the results on the frame
        annotated_frame = results[0].plot()

        # Display the annotated frame
        cv2.imshow("YOLOv8 Tracking", annotated_frame)

        # Break the loop if 'q' is pressed
        if cv2.waitKey(1) & 0xFF == ord("q"):
            break
    else:
        # Break the loop if the end of the video is reached
        break

# Release the video capture object and close the display window
cap.release()
cv2.destroyAllWindows()

Mac 电脑配置yolov8运行环境实现目标追踪、计数、画出轨迹、多线程-LMLPHP

Plotting Tracks 画轨迹

from collections import defaultdict

import cv2
import numpy as np

from ultralytics import YOLO

# Load the YOLOv8 model
model = YOLO("yolov8n.pt")

# Open the video file
video_path = "./video/test_people.mp4"
cap = cv2.VideoCapture(video_path)

# Store the track history
track_history = defaultdict(lambda: [])

# Loop through the video frames
while cap.isOpened():
    # Read a frame from the video
    success, frame = cap.read()

    if success:
        # Run YOLOv8 tracking on the frame, persisting tracks between frames
        results = model.track(frame, persist=True)

        # Get the boxes and track IDs
        boxes = results[0].boxes.xywh.cpu()
        track_ids = results[0].boxes.id.int().cpu().tolist()

        # Visualize the results on the frame
        annotated_frame = results[0].plot()

        # Plot the tracks
        for box, track_id in zip(boxes, track_ids):
            x, y, w, h = box
            track = track_history[track_id]
            track.append((float(x), float(y)))  # x, y center point
            if len(track) > 30:  # retain 90 tracks for 90 frames
                track.pop(0)

            # Draw the tracking lines
            points = np.hstack(track).astype(np.int32).reshape((-1, 1, 2))
            cv2.polylines(annotated_frame, [points], isClosed=False, color=(230, 230, 230), thickness=10)

        # Display the annotated frame
        cv2.imshow("YOLOv8 Tracking", annotated_frame)

        # Break the loop if 'q' is pressed
        if cv2.waitKey(1) & 0xFF == ord("q"):
            break
    else:
        # Break the loop if the end of the video is reached
        break

# Release the video capture object and close the display window
cap.release()
cv2.destroyAllWindows()

Mac 电脑配置yolov8运行环境实现目标追踪、计数、画出轨迹、多线程-LMLPHP

Multithreaded Tracking - 多线程运行示例
  • 这里加载两个模型,运行两个线程,出现线程拥挤、导致无法弹窗,代码需要进一步修改
import threading

import cv2

from ultralytics import YOLO


def run_tracker_in_thread(filename, model, file_index):
    """
    Runs a video file or webcam stream concurrently with the YOLOv8 model using threading.

    This function captures video frames from a given file or camera source and utilizes the YOLOv8 model for object
    tracking. The function runs in its own thread for concurrent processing.

    Args:
        filename (str): The path to the video file or the identifier for the webcam/external camera source.
        model (obj): The YOLOv8 model object.
        file_index (int): An index to uniquely identify the file being processed, used for display purposes.

    Note:
        Press 'q' to quit the video display window.
    """
    video = cv2.VideoCapture(filename)  # Read the video file

    while True:
        ret, frame = video.read()  # Read the video frames

        # Exit the loop if no more frames in either video
        if not ret:
            break

        # Track objects in frames if available
        results = model.track(frame, persist=True)
        res_plotted = results[0].plot()
        cv2.imshow(f"Tracking_Stream_{file_index}", res_plotted)

        key = cv2.waitKey(1)
        if key == ord("q"):
            break

    # Release video sources
    video.release()


# Load the models
model1 = YOLO("yolov8n.pt")
model2 = YOLO("yolov8n-seg.pt")

# Define the video files for the trackers
video_file1 = "video/test_people.mp4"  # Path to video file, 0 for webcam
#video_file2 = 'video/test_traffic.mp4'  # Path to video file, 0 for webcam, 1 for external camera
video_file2 = 0
# Create the tracker threads
tracker_thread1 = threading.Thread(target=run_tracker_in_thread, args=(video_file1, model1, 1), daemon=True)
tracker_thread2 = threading.Thread(target=run_tracker_in_thread, args=(video_file2, model2, 2), daemon=True)

# Start the tracker threads
tracker_thread1.start()
tracker_thread2.start()

# Wait for the tracker threads to finish
tracker_thread1.join()
tracker_thread2.join()

# Clean up and close windows
cv2.destroyAllWindows()


📙 YOLO 系列实战博文汇总如下


🟦 YOLO 理论讲解学习篇
🟧 Yolov5 系列
🟨 YOLOX 系列
🟦 Yolov3 系列
🟨 YOLOX 系列
🟦 持续补充更新

❤️ 人生苦短, 欢迎和墨理一起学AI


Mac 电脑配置yolov8运行环境实现目标追踪、计数、画出轨迹、多线程-LMLPHP

09-27 18:31