Exercices Computer Vision Detecter les contours avec le filtre de Sobel
🎉

Bravo!

Intermédiaire 🧠 Fondamentaux 20 XP 0 personnes ont réussi

Detecter les contours avec le filtre de Sobel

La détection de contours, c'est la base de la détection d'objets. Avant les réseaux de neurones convolutifs, c'était LA technique pour trouver des formes dans une image. Aujourd'hui encore, on l'utilise pour la détection de bords dans les voitures autonomes, l'inspection de pièces industrielles (détecter une fissure sur une pièce métallique), ou la numérisation de documents (trouver les bords d'une feuille de papier pour la recadrer automatiquement).

Les contours, ce sont les endroits où la couleur change brusquement. Pense à un dessin au trait : l'artiste ne dessine que les frontières entre les zones de couleur différentes. Le filtre de Sobel fait pareil automatiquement. Il trouve les zones où l'intensité change vite et les met en valeur.

En pratique, tu utiliserais cv2.Sobel(image, cv2.CV_64F, 1, 0) pour le gradient horizontal et cv2.Sobel(image, cv2.CV_64F, 0, 1) pour le vertical. Ou encore cv2.Canny() qui est un détecteur de contours plus avancé. Ici on implémente Sobel à la main pour comprendre comment fonctionne la convolution avec un kernel directionnel.

Le filtre de Sobel calcule le gradient de l'image dans deux directions :

Gradient horizontal (Gx) : détecte les contours verticaux (les changements d'intensité de gauche à droite)
Gradient vertical (Gy) : détecte les contours horizontaux (les changements de haut en bas)

Les kernels de Sobel sont des matrices 3x3 :

Kernel Gx : -1 0 1 Kernel Gy : -1 -2 -1
-2 0 2 0 0 0
-1 0 1 1 2 1

Pour chaque pixel, on applique ces kernels sur son voisinage 3x3 (multiplication élément par élément puis somme). Le gradient total est la combinaison des deux :

G = sqrt(Gx^2 + Gy^2)

On normalise ensuite entre 0 et 255.

Écris une fonction sobel(image_gris) qui prend une image en niveaux de gris et renvoie l'image des contours (dtype uint8). Les bords de l'image sont laissés à 0.

Exemple :
Une image avec un bord net (moitié noire, moitié blanche) donnera une ligne brillante à l'endroit du bord.

Ce que tu devrais voir sur ta machine : les contours des objets apparaissent en blanc sur fond noir. Les zones uniformes sont noires.

Tests (5/5)

Image uniforme pas de contours
import numpy as np
img = np.full((10, 10), 128, dtype=np.uint8)
result = sobel(img)
assert np.all(result == 0), 'Une image uniforme ne doit pas avoir de contours'
Forme conservee
import numpy as np
img = np.zeros((8, 8), dtype=np.uint8)
result = sobel(img)
assert result.shape == (8, 8), f'Forme attendue (8, 8), obtenue {result.shape}'
Bord net detecte
import numpy as np
img = np.zeros((10, 10), dtype=np.uint8)
img[:, 5:] = 255
result = sobel(img)
assert result[5, 5] > 0 or result[5, 4] > 0, 'Un bord net doit etre detecte'
Dtype uint8
import numpy as np
img = np.zeros((5, 5), dtype=np.uint8)
img[2, 2] = 255
result = sobel(img)
assert result.dtype == np.uint8, f'Le dtype doit etre uint8, obtenu {result.dtype}'
Bords de l image a zero
import numpy as np
img = np.random.randint(0, 255, (6, 6), dtype=np.uint8)
result = sobel(img)
assert result[0, 0] == 0, 'Le coin doit etre a 0'
assert result[0, 3] == 0, 'Le bord superieur doit etre a 0'

Indices (3 disponibles)

solution.py