Das Problem: Strukturierte Daten aus Text extrahieren

Du hast hunderte Geschäftsdokumente, E-Mails oder Berichte und musst daraus systematisch Informationen extrahieren:

  • Firmennamen aus Verträgen
  • Geldbeträge aus Rechnungen
  • Personennamen aus Pressemitteilungen
  • Produktbezeichnungen aus Spezifikationen

Manuell ist das nicht skalierbar. Aber welcher automatisierte Ansatz ist der richtige?


Die 4 NER-Ansätze im Überblick

┌─────────────────────────────────────────────────────────────────┐
│  NER APPROACHES: VON EINFACH BIS KI-POWERED                     │
├─────────────────────────────────────────────────────────────────┤
│                                                                  │
│  ┌──────────────┐     ┌──────────────┐     ┌──────────────┐    │
│  │   REGEX      │────▶│   spaCy      │────▶│   GLiNER     │    │
│  │              │     │              │     │              │    │
│  │ Pattern-     │     │ Rule-based   │     │ Zero-shot    │    │
│  │ Matching     │     │ + Statistical│     │ NER Model    │    │
│  └──────────────┘     └──────────────┘     └──────────────┘    │
│         │                    │                    │             │
│         ▼                    ▼                    ▼             │
│  ┌──────────────┐     ┌──────────────┐     ┌──────────────┐    │
│  │ Schnell,     │     │ Gute Balance │     │ Flexibel,    │    │
│  │ Präzise      │     │ Performance/ │     │ Custom       │    │
│  │ aber rigide  │     │ Genauigkeit  │     │ Entity Types │    │
│  └──────────────┘     └──────────────┘     └──────────────┘    │
│                                                                  │
│                        ┌──────────────┐                         │
│                        │   LLM-based  │                         │
│                        │              │                         │
│                        │ Höchste      │                         │
│                        │ Genauigkeit  │                         │
│                        └──────────────┘                         │
│                               │                                  │
│                               ▼                                  │
│                        ┌──────────────┐                         │
│                        │ Teuer, aber  │                         │
│                        │ versteht     │                         │
│                        │ Kontext      │                         │
│                        └──────────────┘                         │
│                                                                  │
└─────────────────────────────────────────────────────────────────┘

Ansatz 1: Regex – Der Klassiker

Regex ist perfekt für strukturierte, vorhersehbare Muster.

Beispiel: E-Mail-Adressen und Geldbeträge extrahieren

import re

text = """
Kontakt: max.mustermann@firma.de
Rechnungsbetrag: EUR 12.500,00
Ansprechpartner: anna.schmidt@partner.com
Summe: € 8.750,50
"""

# E-Mail-Adressen
email_pattern = r'[\w.-]+@[\w.-]+\.\w+'
emails = re.findall(email_pattern, text)
print(f"E-Mails: {emails}")
# Output: ['max.mustermann@firma.de', 'anna.schmidt@partner.com']

# Geldbeträge (EUR/€ Format)
money_pattern = r'(?:EUR|€)\s*[\d.,]+'
amounts = re.findall(money_pattern, text)
print(f"Beträge: {amounts}")
# Output: ['EUR 12.500,00', '€ 8.750,50']

Wann Regex verwenden?

Gut fürSchlecht für
E-Mail-AdressenPersonennamen
TelefonnummernFirmennamen
DatumsformateKontextabhängige Entitäten
PostleitzahlenVariationen und Tippfehler

Fazit: Regex ist schnell und präzise, aber nur für strukturierte Muster geeignet.


Ansatz 2: spaCy – Der Industriestandard

spaCy bietet trainierte NER-Modelle für Standard-Entitäten.

Installation und Modell laden

pip install spacy
python -m spacy download de_core_news_lg

Beispiel: Entitäten aus Geschäftstext extrahieren

import spacy

nlp = spacy.load("de_core_news_lg")

text = """
Die BMW Group hat heute bekannt gegeben, dass CEO Oliver Zipse
eine Investition von 2,5 Milliarden Euro in das Werk München plant.
Der Aufsichtsrat tagt am 15. März 2026 in Berlin.
"""

doc = nlp(text)

for ent in doc.ents:
    print(f"{ent.text:25}{ent.label_}")

Output:

BMW Group                 → ORG
Oliver Zipse              → PER
2,5 Milliarden Euro       → MONEY
München                   → LOC
15. März 2026             → DATE
Berlin                    → LOC

spaCy Entity Types

LabelBedeutungBeispiele
PERPersonOliver Zipse, Angela Merkel
ORGOrganisationBMW Group, Deutsche Bank
LOCOrtMünchen, Berlin
MONEYGeldbetrag2,5 Milliarden Euro
DATEDatum15. März 2026

Wann spaCy verwenden?

Gut fürSchlecht für
Standard-Entitäten (PER, ORG, LOC)Domänenspezifische Entitäten
Deutsche/Englische TexteCustom Entity Types
ProduktionsumgebungenZero-Shot ohne Training
Batch-VerarbeitungSeltene Entitätstypen

Ansatz 3: GLiNER – Zero-Shot Custom Entities

GLiNER ist ein Zero-Shot NER-Modell: Du definierst beliebige Entity-Typen, ohne zu trainieren.

Installation

pip install gliner

Beispiel: Custom Entities extrahieren

from gliner import GLiNER

model = GLiNER.from_pretrained("urchade/gliner_multi-v2.1")

text = """
Die Tesla Model 3 Performance erreicht eine Reichweite von 547 km
und beschleunigt in 3,3 Sekunden von 0 auf 100 km/h.
CEO Elon Musk präsentierte das Update auf der CES 2026.
"""

# Custom Entity Types definieren
labels = ["Automodell", "Reichweite", "Beschleunigung", "Person", "Event"]

entities = model.predict_entities(text, labels)

for entity in entities:
    print(f"{entity['text']:30}{entity['label']}")

Output:

Tesla Model 3 Performance      → Automodell
547 km                         → Reichweite
3,3 Sekunden von 0 auf 100 km/h → Beschleunigung
Elon Musk                      → Person
CES 2026                       → Event

GLiNER vs spaCy

AspektspaCyGLiNER
Entity TypesVordefiniertFrei definierbar
Training nötig?Für Custom: JaNein (Zero-Shot)
GeschwindigkeitSchnellerLangsamer
GenauigkeitHoch für StandardHoch für Custom
GPU empfohlen?NeinJa

Wann GLiNER verwenden?

Gut fürSchlecht für
Domänenspezifische EntitätenHohe Batch-Volumen
Prototyping ohne TrainingRessourcen-limitierte Umgebungen
Wechselnde Entity-TypenWenn spaCy ausreicht

Ansatz 4: LLM-basierte Extraktion

LLMs wie GPT-4 oder Claude verstehen Kontext und können komplexe Extraktionen durchführen.

Beispiel mit OpenAI

from openai import OpenAI
import json

client = OpenAI()

text = """
In der Vorstandssitzung vom 12.02.2026 wurde beschlossen, dass
Dr. Maria Weber (CFO) und Thomas Klein (CTO) das Joint Venture
mit Siemens AG im Wert von 450 Mio. EUR federführend verhandeln.
Die Unterzeichnung ist für Q2 2026 geplant.
"""

response = client.chat.completions.create(
    model="gpt-4o",
    messages=[
        {
            "role": "system",
            "content": """Extrahiere strukturierte Informationen aus dem Text.
            Antworte als JSON mit folgenden Feldern:
            - personen: Liste von {name, rolle}
            - organisationen: Liste von Firmennamen
            - geldbetraege: Liste von {betrag, waehrung}
            - termine: Liste von {datum, beschreibung}"""
        },
        {"role": "user", "content": text}
    ],
    response_format={"type": "json_object"}
)

result = json.loads(response.choices[0].message.content)
print(json.dumps(result, indent=2, ensure_ascii=False))

Output:

{
  "personen": [
    {"name": "Dr. Maria Weber", "rolle": "CFO"},
    {"name": "Thomas Klein", "rolle": "CTO"}
  ],
  "organisationen": ["Siemens AG"],
  "geldbetraege": [
    {"betrag": "450 Mio.", "waehrung": "EUR"}
  ],
  "termine": [
    {"datum": "12.02.2026", "beschreibung": "Vorstandssitzung"},
    {"datum": "Q2 2026", "beschreibung": "Geplante Unterzeichnung"}
  ]
}

Wann LLM-basierte Extraktion verwenden?

Gut fürSchlecht für
Komplexe, kontextabhängige ExtraktionHohe Volumen (Kosten!)
Strukturierte JSON-AusgabenLatenz-kritische Anwendungen
Relationen zwischen EntitätenDatenschutz-sensible Daten
Unstrukturierte DokumenteWenn einfachere Methoden reichen

Vergleich: Welcher Ansatz für welchen Use Case?

Performance-Vergleich

AnsatzGeschwindigkeitGenauigkeit (Standard)Genauigkeit (Custom)Kosten
Regex⚡⚡⚡⚡⚡⚡⚡⚡⚡⚡ (für Pattern)Gratis
spaCy⚡⚡⚡⚡⚡⚡⚡⚡⚡⚡ (Training nötig)Gratis
GLiNER⚡⚡⚡⚡⚡⚡⚡⚡⚡Gratis
LLM⚡⚡⚡⚡⚡⚡⚡⚡⚡⚡€€€

Entscheidungsbaum

┌─────────────────────────────────────────────────────────────────┐
│  WELCHER NER-ANSATZ?                                            │
├─────────────────────────────────────────────────────────────────┤
│                                                                  │
│  Sind die Entitäten strukturiert (E-Mail, Datum, PLZ)?          │
│  │                                                               │
│  ├── JA → Regex                                                 │
│  │                                                               │
│  └── NEIN ↓                                                     │
│                                                                  │
│  Sind es Standard-Entitäten (Person, Ort, Organisation)?        │
│  │                                                               │
│  ├── JA → spaCy                                                 │
│  │                                                               │
│  └── NEIN ↓                                                     │
│                                                                  │
│  Hast du Zeit/Daten für Training?                               │
│  │                                                               │
│  ├── JA → spaCy Custom Training                                 │
│  │                                                               │
│  └── NEIN ↓                                                     │
│                                                                  │
│  Ist Latenz/Kosten kritisch?                                    │
│  │                                                               │
│  ├── JA → GLiNER                                                │
│  │                                                               │
│  └── NEIN → LLM-basiert                                         │
│                                                                  │
└─────────────────────────────────────────────────────────────────┘

Kombinierter Ansatz: Das Beste aus allen Welten

In der Praxis kombinierst du oft mehrere Ansätze:

import re
import spacy
from gliner import GLiNER

def hybrid_extraction(text):
    results = {}

    # 1. Regex für strukturierte Daten
    results["emails"] = re.findall(r'[\w.-]+@[\w.-]+\.\w+', text)
    results["phone"] = re.findall(r'\+?[\d\s-]{10,}', text)

    # 2. spaCy für Standard-Entitäten
    nlp = spacy.load("de_core_news_lg")
    doc = nlp(text)
    results["persons"] = [ent.text for ent in doc.ents if ent.label_ == "PER"]
    results["organizations"] = [ent.text for ent in doc.ents if ent.label_ == "ORG"]

    # 3. GLiNER für domänenspezifische Entitäten
    gliner = GLiNER.from_pretrained("urchade/gliner_multi-v2.1")
    custom_entities = gliner.predict_entities(text, ["Produktname", "Technologie"])
    results["products"] = [e["text"] for e in custom_entities if e["label"] == "Produktname"]

    return results

Fazit: Der richtige Ansatz für dein Projekt

Quick Summary

Du brauchst…Verwende…
E-Mails, Telefonnummern, PLZRegex
Personen, Orte, OrganisationenspaCy
Custom Entities ohne TrainingGLiNER
Komplexe, kontextabhängige ExtraktionLLM
Alles zusammenHybrid-Ansatz

Meine Empfehlung

  1. Starte mit spaCy – deckt 80% der Fälle ab
  2. Ergänze mit Regex – für strukturierte Muster
  3. Nutze GLiNER für Prototypen – schnell Custom Entities testen
  4. LLM nur wenn nötig – wenn Kontext entscheidend ist

Die beste NER-Lösung ist die, die zu deinem Use Case passt – nicht die technisch aufwändigste.


Ressourcen


Du möchtest Entity Extraction oder NLP in deinem Unternehmen einsetzen? Dann schreib mir einfach auf LinkedIn oder buche direkt einen kostenlosen Call.