Hund und Pferd
Ein Foto genügt: Du lässt ein Modell die Stimmung eines Tieres raten — und stellst deine eigene Einschätzung dagegen. Der spannendste Teil ist, wo die beiden auseinandergehen.
Kurz gesagt
Was: Du machst (oder sammelst) Fotos eines Tieres in verschiedenen Situationen, ordnest jedem Bild zuerst selbst ein Gefühl zu — und lässt dann ein vortrainiertes Bildmodell dasselbe raten. Anschliessend vergleichst du: Wo seid ihr einig, wo nicht?
Der Kern-Gedanke: Kein eigenes Training, reine Inferenz. Du benutzt ein grosses, schon fertiges Modell (CLIP) wie ein Werkzeug und prüfst es kritisch. Der Wert steckt nicht im Code, sondern im Vergleich — und in der Frage, wer eigentlich recht hat, wenn ihr euch uneinig seid.
Du brauchst: ein paar Tierfotos (eigener Hund, eigene Katze, Pferd vom Reiterhof — oder freie
Bilder), Python mit transformers, torch und Pillow. Für die Erweiterung zusätzlich der Kaggle-Datensatz Pet's Facial Expression.
Worum es geht
Ein Hund kann dir nicht sagen, dass er sich fürchtet. Aber sein Körper sagt es laut und deutlich: die eingezogene Rute, die geduckte Haltung, die zurückgelegten Ohren. Genau das haben wir mit meinem Team ausgenutzt und aus einem einzigen Foto die Stimmung eines Hundes bestimmt — mit einer Trefferquote von 60 bis 70 Prozent. Das klingt bescheiden, übertrifft aber, wie Studien zeigen, die meisten Menschen. Bei Pferden lesen wir vor allem Ohren, Augen und Maul; auch dort liegt das Modell bei rund zwei von drei.
Diese Forschungsmodelle sind aufwändig trainiert. Für dich nehmen wir einen anderen, ebenso ehrlichen Weg: ein bereits fertiges Modell, das Bilder und Sprache verbindet, CLIP. Man hält ihm ein Foto und ein paar Beschreibungen hin — „ein ängstlicher Hund“, „ein entspannter Hund“ — und es sagt, welche Beschreibung am besten passt. Du trainierst nichts; du fragst nur und schaust kritisch auf die Antwort.
Bevor du startest
Fotografiere nur Tiere, die du fotografieren darfst, und bedränge sie nicht für ein Bild — ein gestresstes Tier für ein Foto über Stress zu erzeugen, wäre absurd. Am besten fängst du Momente ein, die ohnehin passieren: beim Spielen, beim Dösen, beim Aufmerken. Wer kein Tier zur Hand hat, nimmt freie Bilder aus dem Netz.
Ein bisschen Hintergrund
Ein gemeinsames Gefühlsalphabet. Womit beschriften wir die Gefühle eines Tieres überhaupt? Das Buch greift auf eine Ordnung des Neuropsychologen Jaak Panksepp zurück, der bei allen Säugetieren einige Grundgefühle ausmachte — Erkunden, Spielen, Zuneigung, Angst, Wut, Trauer. Das Schöne: Es ist dasselbe Alphabet für Hund, Pferd und im Kern auch für uns. Für Pferde kommt „Schmerz“ als besonders wichtiges achtes Gefühl hinzu.
Wohin die KI schaut. Die Forschungsmodelle nutzen genau die Stellen, an denen auch wir lesen: beim Pferd Ohren, Augen und Maul, beim Hund die ganze Haltung samt Rute. Als man ein Modell die Tierbilder einmal ganz ohne Etiketten sortieren liess, bildete es sogar Gruppen, die in keine unserer Schubladen passten — vielleicht ein Hinweis auf feinere Tiergefühle, für die uns die Wörter fehlen.
Fotografieren und selbst einschätzen
- Pakete installieren.
pip install transformers torch pillow. - Fotos sammeln. Fünf bis acht Bilder desselben Tieres in klar verschiedenen Situationen: aufmerksam, entspannt, spielend, vielleicht ängstlich. Frontal, gutes Licht, Gesicht und Haltung sichtbar.
- Zuerst du. Notiere zu jedem Bild vor dem Programm deine eigene Einschätzung aus dem Gefühlsalphabet. Das ist wichtig — sonst richtest du dich unbewusst nach der Maschine.
- Dann das Modell. Lass CLIP raten und leg die beiden Urteile nebeneinander.
Das Modell fragen
CLIP versteht Englisch am besten, darum sind die Beschreibungen englisch — die Anzeige bleibt deutsch. Der vollständige Code liegt auf GitHub.
from transformers import CLIPModel, CLIPProcessor
from PIL import Image
import torch
modell = CLIPModel.from_pretrained("openai/clip-vit-base-patch32")
prozessor = CLIPProcessor.from_pretrained("openai/clip-vit-base-patch32")
# Panksepp-Alphabet: deutsches Etikett -> englische Beschreibung fuer CLIP
gefuehle = {
"Freude / Spielen": "a happy, playful dog",
"Zuneigung": "a relaxed, affectionate dog",
"Erkunden": "an alert, curious dog exploring",
"Angst": "a frightened, anxious dog",
"Wut": "an angry, aggressive dog",
"Entspannung": "a calm, resting dog",
}
etiketten = list(gefuehle)
prompts = list(gefuehle.values())
def rate(bilddatei):
bild = Image.open(bilddatei).convert("RGB")
eingabe = prozessor(text=prompts, images=bild, return_tensors="pt", padding=True)
with torch.no_grad():
logits = modell(**eingabe).logits_per_image[0]
wahrsch = logits.softmax(dim=0) # Beschreibungen -> Wahrscheinlichkeiten
beste = int(wahrsch.argmax())
return etiketten[beste], float(wahrsch[beste])
for datei in ["hund1.jpg", "hund2.jpg", "hund3.jpg"]:
label, sicherheit = rate(datei)
print(f"{datei}: Modell rät {label} ({sicherheit:.0%} sicher)")
Was du sehen solltest
Bei deutlichen Bildern (fröhliches Spielen, klares Aufmerken) trifft CLIP oft erstaunlich gut. Bei feinen oder mehrdeutigen Situationen weicht es ab — und manchmal hast du recht, manchmal das Modell, und manchmal ist gar nicht klar, wer recht hat. Genau diese Uneinigkeit ist das eigentliche Ergebnis dieser Aktivität.
Für Pferde
Tausche im Code den Tiernamen und ergänze das achte Gefühl. Bei Pferden zählt der Schmerz besonders:
gefuehle = {
"Aufmerksam": "an alert, attentive horse with ears forward",
"Entspannt": "a calm, relaxed horse",
"Angst": "a frightened horse with ears back and wide eyes",
"Erregung": "an agitated, stressed horse",
"Schmerz": "a horse in pain, with tense face and eyes",
}
Pferde lesen übrigens auch uns — oft feiner, als wir sie lesen. Behalte das im Hinterkopf, wenn du gleich über die Grenzen der Maschine nachdenkst.
Arbeitsblatt
Zwei Urteile nebeneinander
- Trage für jedes Bild dein Urteil und das des Modells ein. In wie vielen von acht Fällen wart ihr einig?
- Suche ein Bild, bei dem ihr nicht einig wart. Wer hat deiner Meinung nach recht — und woran machst du das fest?
- Ein wedelnder Schwanz gilt als Freude. Nenne eine Situation, in der ein Hund wedelt und nicht fröhlich ist. Was heisst das für ein Modell, das nur das Foto sieht?
- Die Trainingsbilder solcher Modelle wurden von Menschen etikettiert. Wie kann sich dadurch ein menschlicher Irrtum in die Maschine fortpflanzen?
- Das Modell liest den Ausdruck. Formuliere in einem Satz, was es damit nicht weiss.
Lösung anzeigen
1. Individuell. Ziel ist, die Übereinstimmung ehrlich zu zählen — und zu merken, dass „oft einig“ nicht „immer einig“ heisst.
2. Individuell. Wichtig ist die Begründung: Berufst du dich auf Ohren/Rute/Haltung — oder auf Kontext, den das Foto gar nicht zeigt (was gerade passiert ist)? Oft liegt die Uneinigkeit daran, dass du den Kontext kennst und das Modell nur das Bild.
3. Hunde wedeln auch bei Erregung, Unsicherheit oder Anspannung. Ein Modell, das nur ein Standbild sieht, kann diese Fälle nicht von Freude unterscheiden — es fehlt Bewegung, Kontext und Vorgeschichte.
4. Lernt das Modell aus Bildern, die Menschen mit ihren Vorannahmen beschriftet haben („sieht traurig aus“), übernimmt es genau diese Vorannahmen — inklusive der Neigung, Tieren menschliche Gefühle anzudichten. Der Fehler steckt dann nicht im Code, sondern in den Etiketten.
5. Es weiss nicht, wie sich das Tier fühlt — nur, wie sein Ausdruck auf dem Bild aussieht. Ausdruck ist ein Hinweis auf den Zustand, kein Beweis, und schon gar kein Blick ins Erleben.
Wenn's klemmt
| Problem | Wahrscheinliche Ursache & Lösung |
|---|---|
| Der erste Lauf dauert lange | CLIP wird einmalig heruntergeladen (einige hundert MB). Danach geht es schnell; Internet beim ersten Mal nötig. |
Image.open scheitert | Falscher Pfad oder kein Bildformat. JPG/PNG verwenden, vollen Pfad angeben. |
| Immer dasselbe Gefühl | Beschreibungen zu ähnlich oder Bild uneindeutig. Prompts klarer trennen (Haltung/Ohren erwähnen), deutlichere Fotos wählen. |
| Sehr niedrige Sicherheiten überall | Normal — CLIP ist kein Tier-Emotions-Spezialist. Es geht um den Vergleich, nicht um hohe Prozente. |
torch lässt sich nicht installieren | Ältere Python-Version. Aktuelles Python nutzen; notfalls die CPU-Variante von torch installieren. |
Zum Nachdenken
- Reine Inferenz ist mächtig: Ein fertiges Modell wird zum Werkzeug, ohne dass du eine einzige Zeile trainierst. Aber „benutzen können“ heisst nicht „blind vertrauen“ — die kritische Frage bleibt deine Aufgabe.
- Der tierische Babelfisch ist ein Hilfsmittel, kein Orakel. Ein wedelnder Schwanz ist nicht immer Freude, und ein Modell, das an einer Rasse gelernt hat, liest eine andere schlechter.
- Der Zweck entscheidet: Zum Wohl des Tieres gelesen — um früh Schmerz oder Dauerstress zu bemerken — ist so ein Leser Fürsorge. Zur Ausbeutung eingesetzt, ist er das Gegenteil.
Erweiterung — selbst trainieren (weiterführend)
Bisher hast du das Modell nur gefragt. Jetzt trainierst du eines selbst — an echten
Daten, wie in der Forschung. Auf Kaggle liegt der Datensatz Pet's Facial Expression
(kaggle.com/datasets/anshtanwar/pets-facial-expression-dataset) mit Gesichtern von Hunden,
Pferden und Katzen, etikettiert nach happy, sad und angry. Statt eines schweren
Bild-Netzes nutzt du einen leichten Trick: CLIP liefert für jedes Bild einen Zahlen-Vektor — seine „Sicht“
des Bildes —, und darauf lernt, genau wie bei der Katze in 12.1, ein einfaches KNN.
import glob, os, numpy as np, torch
from PIL import Image
from sklearn.neighbors import KNeighborsClassifier
from sklearn.model_selection import train_test_split
def bildvektor(datei):
bild = Image.open(datei).convert("RGB")
eingabe = prozessor(images=bild, return_tensors="pt")
with torch.no_grad():
return modell.get_image_features(**eingabe)[0].numpy() # CLIPs Sicht des Bildes
# Ordner je Gefuehl (happy/ sad/ angry/) - Ordnername = Etikett
ORDNER = "pets-facial-expression"
X, y = [], []
for pfad in glob.glob(os.path.join(ORDNER, "**", "*.jpg"), recursive=True):
gefuehl = os.path.basename(os.path.dirname(pfad))
X.append(bildvektor(pfad)); y.append(gefuehl)
X = np.array(X)
print("gelesen:", len(X), "Bilder")
Xtr, Xte, ytr, yte = train_test_split(X, y, test_size=0.25,
random_state=0, stratify=y)
eigenes = KNeighborsClassifier(n_neighbors=5).fit(Xtr, ytr)
print("Treffer auf ungesehenen Bildern:", round(eigenes.score(Xte, yte), 2))
Vergleiche: Trifft dein selbst trainiertes KNN besser als CLIPs blindes Raten aus dem Hauptteil? Und wie verändert sich das Bild, wenn du nur Hunde oder nur Pferde nimmst?
- Wohin schaut das Modell? Mit einer „Wärmekarte“ (Grad-CAM) lässt sich zeigen, welche Bildstellen die Entscheidung tragen. Prüfe: Schaut es wie die Forschungsmodelle auf Ohren, Augen und Maul — oder auf den Hintergrund?
- Mensch und Tier zugleich. Fotografiere Tier und Mensch in einer Szene. Stimmt die Stimmung des einen mit der des anderen? Das ist der erste Schritt zum Lesen des Zusammenspiels — und die Brücke zu den Pflanzen im nächsten Teil.