Seguimiento de Objetos en Movimiento con DeepSORT y YOLOv8 en Python
Este tutorial práctico te guiará en la construcción de un sistema de visión artificial capaz de detectar y rastrear múltiples objetos simultáneamente utilizando YOLOv8 para la detección de alta precisión y DeepSORT para la asignación de identidades consistentes en secuencias de video.
Introducción al Rastreo y Detección de Objetos
El análisis de video en tiempo real es uno de los campos más fascinantes y de mayor crecimiento dentro de la inteligencia artificial y la visión artificial. Mientras que la detección de objetos nos permite identificar qué hay en una imagen y dónde está en un momento dado, el seguimiento de objetos (Object Tracking) va un paso más allá al mantener una identidad única para cada objeto a lo largo de una secuencia de cuadros.
En este tutorial completo, combinaremos dos de las herramientas más potentes del ecosistema actual:
- YOLOv8 (You Only Look Once v8): Desarrollado por Ultralytics, es el estado del arte en detección de objetos por su increíble velocidad y precisión.
- DeepSORT (Simple Online and Realtime Tracking with a Deep Association Metric): Un algoritmo robusto que utiliza filtros de Kalman y redes neuronales profundas para asociar características de apariencia y mantener las identidades de los objetos incluso cuando se ocluyen temporalmente.
Al finalizar este tutorial, serás capaz de desplegar tu propio sistema capaz de contar personas, seguir vehículos en autopistas o analizar flujos de tráfico con código totalmente funcional en Python.
Requisitos Previos y Configuración del Entorno
Antes de escribir código, debemos preparar nuestro entorno de desarrollo. Necesitaremos instalar Python (recomendamos la versión 3.10 o superior) y las bibliotecas necesarias para el procesamiento de imágenes y modelos de aprendizaje profundo.
Instalación de Dependencias
Abre tu terminal o consola de comandos y crea un entorno virtual para mantener tu proyecto limpio y ordenado. Luego, instala los paquetes requeridos:
python -m venv venv
source venv/bin/activate # En Windows usa: venv\Scripts\activate
pip install --upgrade pip
pip install ultralytics opencv-python numpy filterpy
Verificación de la Instalación
Para asegurarte de que todo funciona correctamente, puedes ejecutar un breve script de prueba para comprobar que PyTorch y OpenCV reconocen tu hardware (CPU o GPU):
import cv2
import ultralytics
print("Versión de OpenCV:", cv2.__version__)
print("Versión de Ultralytics:", ultralytics.__version__)
ultralytics.checks()
Arquitectura del Sistema: ¿Cómo Funciona YOLOv8 + DeepSORT?
Para entender el código que escribiremos más adelante, es fundamental comprender cómo interactúan la detección y el seguimiento. El proceso ocurre en cada cuadro de video de forma secuencial.
El flujo de trabajo detallado consta de los siguientes pasos:
Implementación del Código Base
Vamos a construir nuestro script principal paso a paso. Crearemos un archivo llamado tracker.py en el directorio de tu proyecto.
Importación de Librerías y Carga del Modelo
Comenzaremos importando las librerías necesarias y cargando el modelo preentrenado de YOLOv8. Usaremos el modelo estándar yolov8n.pt (nano) por razones de velocidad, pero puedes cambiarlo a yolov8s.pt o superior si buscas mayor precisión.
import cv2
import numpy as np
from ultralytics import YOLO
# Cargar el modelo YOLOv8 preentrenado en COCO
model = YOLO("yolov8n.pt")
# Inicializar la captura de video (0 para webcam o ruta a archivo de video)
video_path = "tu_video_de_prueba.mp4"
cap = cv2.VideoCapture(video_path)
# Obtener propiedades del video
width = int(cap.get(cv2.CAP_PROP_FRAME_WIDTH))
height = int(cap.get(cv2.CAP_PROP_FRAME_HEIGHT))
fps = int(cap.get(cv2.CAP_PROP_FPS))
print(f"Video cargado correctamente: {width}x{height} a {fps} FPS")
Integración del Rastreo Nativo y Personalizado
Aunque existen implementaciones externas complejas para DeepSORT, Ultralytics YOLOv8 incluye soporte nativo optimizado para algoritmos de seguimiento como BoT-SORT y ByteTRACK, los cuales ofrecen un rendimiento equivalente o superior a DeepSORT con menor complejidad de integración. A continuación, implementaremos el bucle de procesamiento utilizando el rastreador integrado de YOLOv8.
# Bucle principal de procesamiento de video
while cap.isOpened():
success, frame = cap.read()
if not success:
print("Fin del video o error al leer el cuadro.")
break
# Ejecutar seguimiento con YOLOv8 (usando persist=True para mantener IDs)
# Puedes cambiar tracker='botsort.yaml' o 'bytetrack.yaml'
results = model.track(frame, persist=True, tracker="bytetrack.yaml", verbose=False)
# Extraer cajas y resultados de seguimiento
current_frame = results[0].plot()
# Mostrar el resultado en una ventana interactiva
cv2.imshow("Sistema de Seguimiento - Visión Artificial", current_frame)
# Romper el bucle si se presiona la tecla 'q'
if cv2.waitKey(1) & 0xFF == ord('q'):
break
# Liberar recursos
cap.release()
cv2.destroyAllWindows()
Filtrado y Análisis Avanzado de Trayectorias
Una vez que somos capaces de rastrear objetos y asignarles un identificador único (ID), el siguiente nivel en visión artificial consiste en extraer información analítica útil a partir de esas trayectorias.
Extracción de Coordenadas y Conteo de Objetos
Modificaremos nuestro bucle para acceder directamente a las coordenadas de las cajas delimitadoras (boxes), las confianzas y los identificadores de seguimiento (track_id), permitiéndonos contar cuántos objetos únicos han aparecido en la escena.
# Inicializar conjunto para almacenar IDs únicos detectados
seen_ids = set()
while cap.isOpened():
success, frame = cap.read()
if not success:
break
results = model.track(frame, persist=True, tracker="bytetrack.yaml", verbose=False)
# Verificar si hay cajas detectadas con IDs de seguimiento
if results[0].boxes.id is not None:
boxes = results[0].boxes.xyxy.cpu().numpy()
track_ids = results[0].boxes.id.int().cpu().numpy()
confidences = results[0].boxes.conf.cpu().numpy()
classes = results[0].boxes.cls.int().cpu().numpy()
for box, track_id, conf, cls in zip(boxes, track_ids, confidences, classes):
seen_ids.add(track_id)
x1, y1, x2, y2 = map(int, box)
class_name = model.names[cls]
# Dibujar caja personalizada y etiqueta
cv2.rectangle(frame, (x1, y1), (x2, y2), (0, 255, 0), 2)
label = f"{class_name} ID:{track_id} ({conf:.2f})"
cv2.putText(frame, label, (x1, y1 - 10), cv2.FONT_HERSHEY_SIMPLEX, 0.5, (0, 255, 0), 2)
# Mostrar contador total en pantalla
cv2.putText(frame, f"Objetos Únicos Totales: {len(seen_ids)}", (30, 50),
cv2.FONT_HERSHEY_SIMPLEX, 1, (0, 0, 255), 2)
cv2.imshow("Análisis Avanzado", frame)
if cv2.waitKey(1) & 0xFF == ord('q'):
break
cap.release()
cv2.destroyAllWindows()
Optimización del Rendimiento
Cuando trabajamos con secuencias de video en alta definición (1080p o 4K), el procesamiento por cuadro puede volverse lento. Aquí tienes una tabla comparativa de estrategias para optimizar tu sistema:
| Estrategia de Optimización | Descripción | Impacto en Precisión | Impacto en Velocidad |
|---|---|---|---|
| --- | --- | --- | --- |
| Reducción de Resolución | Escalar el video a 640x640 antes de la inferencia. | Bajo | Muy Alto 🚀 |
| Uso de Modelos Nano/Small | Utilizar yolov8n en lugar de yolov8m o yolov8x. | Moderado | Alto ⚡ |
| --- | --- | --- | --- |
| Inferencia con TensorRT | Exportar el modelo a formato TensorRT para GPUs NVIDIA. | Ninguno | Extremo 🔥 |
| Salto de Cuadros (Frame Skipping) | Procesar solo 1 de cada N cuadros para el rastreo. | Moderado | Alto 📈 |
yolo export model=yolov8n.pt format=engine para generar un motor TensorRT ultra rápido.Preguntas Frecuentes (FAQ)
¿Qué diferencia hay entre ByteTRACK y DeepSORT?
ByteTRACK es un algoritmo de seguimiento basado en la asociación de todas las cajas detectadas (incluso las de baja puntuación) en lugar de depender únicamente de la apariencia visual mediante redes neuronales secundarias. Esto lo hace generalmente más rápido y eficiente en escenarios concurridos.¿Cómo puedo contar objetos que cruzan una línea virtual?
Puedes definir una línea mediante dos puntos `(x1, y1)` y `(x2, y2)` en tu espacio de video y evaluar si las coordenadas del centroide o la base de la caja delimitadora cruzan dicha línea utilizando ecuaciones de producto cruzado vectorial.¿Funciona este sistema con múltiples cámaras?
Para múltiples cámaras se requiere un paso adicional llamado Re-Identificación (Re-ID) multicanal y correspondencia global, ya que el algoritmo estándar de este tutorial opera sobre una única fuente de video continua.Conclusión
¡Felicidades! Has implementado con éxito un sistema completo de detección y seguimiento de objetos utilizando YOLOv8 y algoritmos de rastreo avanzados en Python. Este tipo de arquitecturas son la base fundamental para sistemas modernos de videovigilancia inteligente, análisis deportivo, vehículos autónomos y automatización industrial.
Te animamos a experimentar modificando los umbrales de confianza, probando diferentes modelos de YOLO y adaptando el código para resolver problemas específicos en tus propios proyectos de inteligencia artificial.
Tutoriales relacionados
- Detección y Reconocimiento de Placas de Matrícula (LPR) con OpenCV y Tesseract OCRintermediate20 min
- Reconocimiento de Emociones Faciales con OpenCV y Redes Convolucionales (CNNs)intermediate20 min
- Estimación de la Profundidad y Reconstrucción 3D con Cámaras RGB-D y Open3Dintermediate20 min
- Detección de Objetos en Tiempo Real con YOLOv5 y OpenCV: Un Tutorial Prácticointermediate20 min
- Alineación y Calibración de Cámaras para Visión Estereoscópica 👁️🗨️intermediate15 min
Comentarios (0)
Aún no hay comentarios. ¡Sé el primero!