ANPR avec YOLOV8

ANPR avec YOLOV8' -> 'ANPR avec YOLOV8

Photo de Semyon Borisov sur Unsplash

Introduction :

YOLO V8 est le dernier modèle développé par l’équipe d’Ultralytics. C’est un modèle YOLO de pointe qui dépasse ses prédécesseurs en termes de précision et d’efficacité.

https://github.com/ultralytics/ultralytics

Il est facile à utiliser et accessible en ligne de commande ou via le package Python. Il offre une prise en charge prête à l’emploi pour la détection d’objets, la classification et les tâches de segmentation. Il a récemment ajouté une prise en charge native pour le suivi d’objets, de sorte que nous n’aurons pas à nous préoccuper de cloner des dépôts d’algorithmes de suivi.

Dans cet article, je vais passer en revue les étapes de l’utilisation de YOLOV8 pour construire un outil de reconnaissance automatique des plaques d’immatriculation (ANPR). Alors, commençons.

Suivi des véhicules :

Comme nous l’avons mentionné précédemment, YOLOV8 dispose d’un suivi natif, donc cette étape est assez simple. Tout d’abord, installez le package Ultralytics

pip install ultralytics

Ensuite, nous devons lire les images vidéo avec OpenCV et appliquer la méthode de suivi du modèle avec l’argument persist réglé sur True pour garantir que les identifiants persistent dans le cadre suivant. Le modèle renvoie les coordonnées pour dessiner une boîte englobante ainsi que l’identifiant, l’étiquette et le score

import cv2from ultralytics import YOLOmodel = YOLO('yolov8n.pt')cap = cv2.VideoCapture("test_vids/vid1.mp4")ret = Truewhile ret:    # Lire un cadre de la caméra    ret, frame = cap.read()    if ret and frame_nbr % 10 == 0 :        results = model.track(frame,persist=True)        for result in results[0].boxes.data.tolist():            x1, y1, x2, y2, id, score,label = result            # Vérifier si le seuil est atteint et si l'objet est une voiture            if score > 0.5 and label==2:                cv2.rectangle(frame, (int(x1), int(y1)), (int(x2), int(y2)), (0, 255, 0), 4)                text_x = int(x1)                text_y = int(y1) - 10                cv2.putText(frame, str(id), (text_x, text_y),                           cv2.FONT_HERSHEY_SIMPLEX, 0.8, (0, 255, 0), 2)                cropped_img = frame[int(y1):int(y2), int(x1):int(x2)]

Voici le résultat sur une image :

image fournie par l'auteur

Les coordonnées des boîtes englobantes sont ensuite utilisées pour recadrer chaque voiture dans l’image.

Reconnaissance des plaques d’immatriculation :

Maintenant que nous avons nos voitures, nous devons détecter les plaques d’immatriculation, pour cela, nous devons entraîner le modèle Yolo. Pour cela, j’ai utilisé l’ensemble de données Kaggle suivant.

Détection des plaques d’immatriculation de voiture

433 images de plaques d’immatriculation

www.kaggle.com

Cependant, les étiquettes de cet ensemble de données sont au format XML PASCAL VOC :

<annotation>    <folder>images</folder>    <filename>Cars105.png</filename>    <size>        <width>400</width>        <height>240</height>        <depth>3</depth>    </size>    <segmented>0</segmented>    <object>        <name>licence</name>        <pose>Unspecified</pose>        <truncated>0</truncated>        <occluded>0</occluded>        <difficult>0</difficult>        <bndbox>            <xmin>152</xmin>            <ymin>147</ymin>            <xmax>206</xmax>            <ymax>159</ymax>        </bndbox>    </object></annotation>

YOLO a besoin des annotations de chaque image dans un fichier avec le format suivant: étiquette, centre x, centre y, largeur, hauteur

Ce code gère cette transformation de nos données:

def xml_to_yolo(bbox, w, h):    # xmin, ymin, xmax, ymax    x_center = ((bbox[2] + bbox[0]) / 2) / w    y_center = ((bbox[3] + bbox[1]) / 2) / h    width = (bbox[2] - bbox[0]) / w    height = (bbox[3] - bbox[1]) / h    return [x_center, y_center, width, height]def convert_dataset():    for filename in os.listdir("annotations"):        tree = ET.parse(f"annotations/{filename}")        root = tree.getroot()        name = root.find("filename").text.replace(".png", "")        width = int(root.find("size").find("width").text)        height = int(root.find("size").find("height").text)        for obj in root.findall('object'):            box = []            for x in obj.find("bndbox"):                box.append(int(x.text))            yolo_box = xml_to_yolo(box, width, height)            line = f"0 {yolo_box[0]} {yolo_box[1]} {yolo_box[2]} {yolo_box[3]}"            with open(f"train/labels/{name}.txt", "a") as file:                # Écrire une ligne dans le fichier                file.write(f"{line}\n")

maintenant, il ne reste plus qu’à configurer notre fichier de configuration yaml avec les chemins vers les dossiers de données d’entraînement et de validation, puis entraîner le modèle note (les noms de dossier à l’intérieur des dossiers d’entraînement et de validation doivent être labels et images). Ensuite, nous le passons en argument à notre instance de modèle et commençons l’entraînement

path: C:/Users/msi/PycharmProjects/ANPR_Yolov8train: trainval: val# Classesnames:  0: plaque d'immatriculation

model = YOLO('yolov8n.yaml')result = model.train(data="config.yaml",device="0",epochs=100,verbose=True,plots=True,save=True)
image by author

Maintenant que nous avons notre modèle de plaque d’immatriculation, il nous suffit de le charger et de l’utiliser sur les images de voiture recadrées de la vidéo, nous appliquons le niveau de gris sur le recadrage de la plaque d’immatriculation et utilisons easy_ocr pour lire son contenu

cropped_img = frame[int(y1):int(y2), int(x1):int(x2)]plates = lp_detector(cropped_img)for plate in plates[0].boxes.data.tolist():    if score > 0.6:          x1, y1, x2, y2, score, _ = plate          cv2.rectangle(cropped_img, (int(x1), int(y1)), (int(x2), int(y2)), (255, 0, 0), 2)          lp_crop = cropped_img[int(y1):int(y2), int(x1):int(x2)]          lp_crop_gray = cv2.cvtColor(lp_crop, cv2.COLOR_BGR2GRAY)          ocr_res = reader.readtext(lp_crop_gray)          if not ocr_res:                print("Aucune plaque détectée")           else:               entry = {'id': id, 'number': ocr_res[0][1], 'score': ocr_res[0][2]}               update_csv(entry)               out.write(frame)                cv2.imshow('frame', frame)        frame_nbr += 1

la fonction update_csv écrira l’identifiant de la voiture et le numéro de plaque d’immatriculation dans un fichier CSV. Et voilà le pipeline ANPR avec yolov8

image by author

Conclusion:

Comme nous l’avons vu, YOLOV8 simplifie le processus de construction d’un pipeline ANPR car il offre un suivi natif et une détection d’objets.

ce dépôt contient le projet complet où j’ai construit une application ANPR avec streamlit:

GitHub – skandermenzli/ANPR_Yolov8

Contribuer au développement de skandermenzli/ANPR_Yolov8 en créant un compte sur GitHub.

github.com

We will continue to update IPGirl; if you have any questions or suggestions, please contact us!

Share:

Was this article helpful?

93 out of 132 found this helpful

Discover more

AI

IA générative dans le domaine de la santé

Introduction L’intelligence artificielle générative a connu un regain d’intérêt ces dernières années. Il ...

Science des données

Rencontrez ChatDB un cadre qui augmente les LLM avec une mémoire symbolique sous forme de bases de données.

Les modèles de langage de grande taille, tels que GPT-4 et PaLM 2, sont devenus une partie cruciale des systèmes d...

AI

Intégration facile de l'application GenAI à l'aide de l'API Segmind et de Postman

Introduction L’intégration de l’intelligence artificielle (IA) dans nos applications devient de plus en p...

AI

Étendez vos GPT avec C#

Cet article démontre comment créer un GPT en utilisant OpenAI et l'étendre avec votre propre code C# en utilisant AIN...

AI

Le Tencent AI Lab présente Chain-of-Noting (CoN) pour améliorer la robustesse et la fiabilité des modèles de langage améliorés par la recherche.

Les chercheurs du Tencent AI Lab abordent les défis liés à la fiabilité des modèles de langage augmentés par la récup...