Features: von Pixeln zu Vektoren
Logistic Regression, SVM und Random Forest können nichts mit einem Bild anfangen — sie erwarten einen Zahlenvektor fester Länge pro Beispiel. Dieser Schritt entscheidet bei den klassischen Verfahren über Erfolg oder Misserfolg: Das Modell kann nur Muster finden, die in den Features überhaupt noch drinstecken.
Option 1: Flatten — die naive Variante
Einfach alle Pixel hintereinander in einen Vektor schreiben: 256×256×3 = 196.608 Dimensionen. Funktioniert formal, ist aber fast immer eine schlechte Idee: riesig, langsam, und ein um 3 Pixel verschobenes Blatt ergibt einen komplett anderen Vektor.
Option 2: Farb-Histogramme — der PlantVillage-Favorit
Krankheiten verändern vor allem die Farbe: braune Flecken, gelbe Ränder, weißer Belag. Ein Histogramm zählt, wie viele Pixel in welchen Farbbereich fallen — egal wo im Bild sie liegen. Damit ist es robust gegen Verschiebung und Rotation.
import cv2
import numpy as np
def extrahiere_features(pfad, bins=(8, 8, 8)):
bild = cv2.imread(str(pfad))
bild = cv2.resize(bild, (128, 128))
hsv = cv2.cvtColor(bild, cv2.COLOR_BGR2HSV)
# 3D-Histogramm über Hue, Saturation, Value: 8*8*8 = 512 Werte
hist = cv2.calcHist([hsv], [0, 1, 2], None, bins,
[0, 180, 0, 256, 0, 256])
hist = cv2.normalize(hist, hist).flatten()
return hist # Vektor mit 512 Zahlen, Summe der Quadrate = 1
X_train_feat = np.array([extrahiere_features(p) for p in X_train])
X_test_feat = np.array([extrahiere_features(p) for p in X_test])
print(X_train_feat.shape) # (38000, 512)HSV statt RGB, weil dort der Farbton (Hue) ein eigener Kanal ist — „braun vs. grün“ steckt dann in einer einzigen Dimension statt verschmiert über drei.
Option 3: Textur-Features
Manche Krankheiten ändern weniger die Farbe als die Oberfläche: Mehltau wirkt pudrig, Schorf rau. Dafür gibt es Textur-Deskriptoren wie HOG (Histogram of Oriented Gradients — Kantenrichtungen zählen) oder LBP (Local Binary Patterns — lokale Hell/Dunkel-Muster). In der Praxis kombiniert man oft: Farb-Histogramm + Textur, per np.concatenate zu einem Vektor.
Und das CNN?
Das CNN überspringt diese ganze Lektion: Es bekommt die Pixel roh und lernt in seinen Convolution-Schichten selbst, welche Farb- und Texturmuster relevant sind. Das ist sein fundamentaler Vorteil — und der Grund, warum es mehr Daten und Rechenzeit braucht. Handgebaute Features sind komprimiertes Vorwissen; das CNN muss sich dieses Wissen erst ertrainieren.
Warum eigentlich? — Warum reicht ein Histogramm hier so erstaunlich gut?
Häufiger Denkfehler — Features nach dem Skalieren neu erfinden
cv2.imread BGR liefert, nicht RGB. Wer danach mit COLOR_RGB2HSV konvertiert, vertauscht still Rot und Blau — der Code läuft fehlerfrei durch, nur die Features sind Unsinn. Solche stillen Fehler findet kein Compiler, nur ein Plot-Check der Zwischenschritte.