| from ultralytics import YOLO |
| import numpy as np |
| from typing import List, Dict, Any, Union |
| from pathlib import Path |
|
|
| class PotholeDetector: |
| _instance = None |
| _model = None |
| |
| def __new__(cls, model_path: Union[str, Path]): |
| if cls._instance is None: |
| cls._instance = super(PotholeDetector, cls).__new__(cls) |
| |
| cls._instance._model = YOLO(str(model_path)) |
| return cls._instance |
|
|
| @classmethod |
| def get_instance(cls, model_path: Union[str, Path] = "yolov8n.pt"): |
| if cls._instance is None: |
| return cls(model_path) |
| return cls._instance |
| |
| def predict(self, image: Union[np.ndarray, str, Path], conf_thresh: float = 0.25) -> List[Dict[str, Any]]: |
| """ |
| Runs YOLOv8 object detection inference. |
| |
| Inputs: |
| image: Image payload represented as absolute Path string or physical BGR matrix natively. |
| conf_thresh: Decimal threshold constraint evaluating bounding strictness minimums. |
| |
| Outputs: |
| Rigorous dictionary format: {'xyxy': [x1, y1, x2, y2], 'confidence': float, 'class_id': int} |
| """ |
| |
| results = self._model.predict(source=image, conf=conf_thresh, verbose=False) |
| |
| detections = [] |
| for r in results: |
| boxes = r.boxes |
| if boxes is None or len(boxes) == 0: |
| continue |
| for box in boxes: |
| xyxy = box.xyxy[0].cpu().numpy().tolist() |
| conf = float(box.conf[0].cpu().numpy()) |
| cls_id = int(box.cls[0].cpu().numpy()) |
| detections.append({'xyxy': xyxy, 'confidence': conf, 'class_id': cls_id}) |
| |
| return detections |
|
|