Ein Unternehmen setzt ein lokales 13B-Modell auf, schaltet es für zehn interne Nutzer frei. Die erste Woche läuft problemlos. Dann kommt ein zweites Team, fügt einen weiteren Use-Case hinzu, die Anzahl gleichzeitiger Requests springt auf 20–30, und die Antwortzeit steigt von drei Sekunden auf 40. Jemand schlägt vor, eine stärkere GPU zu kaufen. Die GPU wird gekauft. Die Antwortzeit sinkt auf 25 Sekunden. Das Problem ist nicht die Hardware — das Problem ist, was unter der Haube mit dem KV-Cache und dem Batching passiert.
Throughput und Latenz bei der LLM-Inferenz sind nicht nur eine Hardware-Frage. Sie sind eine Architektur-Frage. Wie ein Serving-Framework den Speicher verwaltet, wie es Requests batcht, wie es Zwischenergebnisse teilt — das entscheidet, ob Sie aus einer GPU die Effizienz entsprechend ihrem Kaufpreis herausholen oder für Leistung bezahlen, die nie genutzt wird. Dieser Artikel erklärt die Mechanismen und zeigt, wo die Stellschrauben zur Verbesserung liegen — ohne zusätzliche Hardware.
Wo Leistung verloren geht: Anatomie der LLM-Inferenz
Um zu verstehen, wo sich optimieren lässt, muss man zunächst verstehen, was bei der Textgenerierung passiert. Die LLM-Inferenz läuft in zwei Phasen ab.
Die Prefill-Phase verarbeitet den gesamten Eingabe-Prompt auf einmal — eine parallelisierbare Operation, die die GPU ähnlich wie Matrixmultiplikation auslastet. Das Ergebnis sind Key- und Value-Vektoren (KV) für jeden Eingabe-Token, die im Speicher abgelegt werden. Die Zeit, die diese Phase benötigt, wird als TTFT bezeichnet — Time to First Token. Genau TTFT bestimmt, wann der Nutzer das erste Zeichen der Antwort sieht.
Die Decode-Phase generiert Token für Token, wobei jeder neue Token von allen vorherigen abhängt. Das ist eine sequenzielle Operation — sie lässt sich innerhalb eines einzelnen Requests nicht parallelisieren. Die Generierungsgeschwindigkeit wird in Tokens pro Sekunde gemessen (tokens/sec).
Entscheidende Erkenntnis: Prefill ist compute-bound (belastet die GPU-Kerne), Decode ist memory-bound (belastet die Speicherbandbreite). Diese beiden Phasen haben unterschiedliche Bottlenecks und erfordern unterschiedliche Optimierungen. Die meisten naiven Implementierungen opfern den Throughput zugunsten von Einfachheit.
Statisches Batching: Warum es bei gemischten Lasten versagt
Der klassische Ansatz beim Batching ist einfach: Man wartet, bis eine Charge von Requests gefüllt ist, sendet alle auf einmal, das Modell verarbeitet sie parallel, die Ergebnisse kommen zurück. Dann wartet man auf den nächsten Batch.
Das Problem tritt auf, wenn Requests unterschiedlich lang sind — was im Alltag die Regel ist. Ein Request braucht eine einzeilige Antwort, ein anderer generiert 500 Token. Statisches Batching wartet, bis der längste Request im Batch fertig ist. Andere GPU-Kerne, die bereits einen neuen Request beginnen könnten, sitzen untätig. Die effektive GPU-Auslastung fällt bei typischer gemischter Last auf 20–40 %.
Bei realen Workloads bedeutet das: Die GPU, für die Sie bezahlen, wartet die meiste Zeit. Nicht auf Daten, nicht auf das Netzwerk — sie wartet auf einen einzelnen langsamen Request.
Continuous Batching: Dynamisches Nachfüllen des Batches
Continuous Batching löst dieses Problem anders. Anstatt auf das Ende des Batches zu warten, wird jeder generierte Token zur Gelegenheit: Der Server schaut in die Warteschlange der ausstehenden Requests und fügt sofort neue zum laufenden Batch hinzu. Ein abgeschlossener Request gibt seinen Platz sofort für einen neuen frei — ohne Unterbrechung.
Das Ergebnis ist dramatisch: Auf derselben Hardware erreicht Continuous Batching bei gemischten Lasten typischerweise einen 2–3-fach höheren Throughput gegenüber statischem Batching. Nicht weil die GPU schneller wäre, sondern weil ungenutzte Zyklen mit neuen Requests gefüllt werden.
vLLM, SGLang und TGI implementieren Continuous Batching nativ. Ollama implementiert es nicht vollständig — es ist für den Single-User-Desktop-Betrieb optimiert, nicht für produktive Multi-User-Lasten. Für ein Team mit einem Dutzend gleichzeitiger Nutzer ist der Unterschied spürbar: Bei acht parallelen Requests ist vLLM bei gleicher Hardware deutlich leistungsfähiger als Ollama. Einen detaillierten Vergleich der Serving-Frameworks finden Sie im Artikel vLLM vs. SGLang vs. Ollama.
KV-Cache: Wo VRAM bei langen Kontexten „verschwindet"
Jeder Token, den das Modell verarbeitet — ob in der Prefill- oder Decode-Phase — erzeugt für jede Attention-Schicht einen Key- und Value-Vektor. Diese Vektoren müssen gespeichert werden, damit sie bei der Generierung des nächsten Tokens nicht neu berechnet werden müssen. Dieses Speicherwerk nennt sich KV-Cache.
Die Größe des KV-Cache wächst linear mit der Kontextlänge. Zur Orientierung: Ein 70B-Modell mit einem 128K-Kontextfenster benötigt allein für den KV-Cache grob im Bereich von mehreren Dutzend Gigabyte — zusätzlich zum VRAM, den das Modell selbst belegt. Bei vier parallelen Requests mit derselben Kontextlänge vervierfacht sich das entsprechend.
Moderne Modelle implementieren mehrheitlich Grouped Query Attention (GQA), das die KV-Cache-Größe gegenüber klassischem Multi-Head-Attention drastisch reduziert, indem Gruppen von Query-Heads gemeinsame Key- und Value-Vektoren teilen. Die meisten aktuellen Modellfamilien (Llama, Qwen, Mistral) nutzen GQA — das ist heute Standard, keine Ausnahme.
Eine weitere Stellschraube ist die KV-Cache-Quantisierung: Die Reduzierung der Präzision der KV-Vektoren auf INT8 oder FP8 kann deren Größe bei minimalem Qualitätsverlust der Ausgaben halbieren. Produktive Serving-Frameworks unterstützen dies als optionale Optimierung.
Praktische Konsequenz: Wenn der VRAM knapp wird und Sie über lange Kontexte nachdenken, ist der KV-Cache der erste Ort, an dem Sie nach der Ursache suchen sollten. Bevor Sie eine neue GPU kaufen, lohnt es sich zu messen, wie viel VRAM der KV-Cache bei Ihrer typischen Last tatsächlich belegt.
PagedAttention: Virtuelles Paging für den KV-Cache
Naive KV-Cache-Verwaltung schafft ein weiteres Problem: Sie reserviert Speicher für die maximal mögliche Kontextlänge im Voraus, auch wenn die meisten Requests deutlich kürzer sind. Stellen Sie sich vor, Sie allokieren 128K Slots, weil das Modell das technisch schafft, der durchschnittliche Request aber nur 2.000 Token lang ist. Der Großteil des allozierten Speichers liegt leer — und durch Fragmentierung lässt er sich nicht effizient wiederverwenden.
PagedAttention, die zentrale Innovation von vLLM, löst dieses Problem inspiriert vom Betriebssystem-Design. Genau wie ein OS den RAM in physische Blöcke einteilt und diese virtuell abbildet, unterteilt PagedAttention den KV-Cache in Blöcke fester Größe (Seiten), die dynamisch zugeteilt werden — entsprechend der tatsächlich generierten Token eines Requests. Speicher wird on-demand allokiert, nicht im Voraus.
Das Ergebnis: Die Fragmentierung des KV-Cache sinkt von typischerweise 60–80 % Verschwendung auf unter 4 %. Derselbe VRAM bedient damit ein Vielfaches mehr an parallelen Requests, oder dieselbe Anzahl von Requests mit längerem Kontext.
Für den Produktionsbetrieb ist das ein Unterschied, der direkt beeinflusst, wie viele GPUs Sie benötigen — und damit die Serving-Kosten.
Latenz vs. Throughput: Das sind nicht dasselbe
Einer der häufigsten Denkfehler: Throughput-Optimierung und Latenz-Optimierung sind teilweise gegenläufige Ziele.
Throughput misst, wie viele Token (oder Requests) der Server pro Sekunde in der Summe generiert — relevant bei Batch-Workloads, Offline-Dokumentenverarbeitung, APIs mit hohem Volumen.
Latenz misst, wie schnell ein einzelner Nutzer seine Antwort erhält — TTFT und die Gesamtzeit bis zum Ende der Generierung. Relevant bei interaktiven Anwendungen, Chatbots, Copilots.
Das Problem entsteht, wenn Continuous Batching aggressiv eingesetzt wird: Der Server kann das Senden der Antwort absichtlich verzögern, um einen größeren Batch zu füllen — höherer Throughput, aber schlechtere Latenz für den einzelnen Nutzer. Die meisten Produktions-Frameworks haben Parameter (--max-num-seqs, scheduler-delay-factor), mit denen sich dieser Trade-off nach Priorität einstellen lässt.
Für interaktive Anwendungen ist es in der Regel die richtige Strategie, TTFT zu priorisieren — ein Nutzer, der die ersten Token innerhalb von zwei Sekunden sieht, nimmt das System als „schnell" wahr, auch wenn die vollständige Generierung länger dauert. Streaming-Antworten (SSE oder WebSocket) verbessern diese Wahrnehmung zusätzlich, ohne den tatsächlichen Throughput zu verändern.
Beim Vergleich von Serving-Lösungen: SGLang erreicht bei prefix-lastigen Workloads auf derselben Hardware einen etwa ein Fünftel niedrigeren TTFT als vLLM — bei interaktiven Anwendungen ein spürbarer Unterschied. Bei reinem Batch-Serving ist die Differenz geringer.
Prefix-Caching und KV-Cache-Sharing
Wenn mehrere Requests mit demselben System-Prompt beginnen — was bei Produktionsanwendungen üblich ist — berechnet jeder Request denselben Prefix neu. Das ist Verschwendung: Der Prefill derselben 500 System-Prompt-Token 1.000-mal täglich.
Prefix-Caching (auch Prompt Caching) löst dieses Problem: Der Server speichert die KV-Ergebnisse des Prefixes und liest sie beim nächsten Request mit identischem Anfang aus dem Cache, anstatt sie neu zu berechnen. Der Effekt ist zweifach — es senkt sowohl die Latenz (TTFT für gecachte Prefixe liegt nahe null) als auch die Rechenkosten.
SGLang implementiert dies über RadixAttention — einen LRU-Cache von KV-Werten, der als Radix-Trie organisiert ist und automatisch den längsten gemeinsamen Prefix zwischen Requests findet und teilt. Bei Workloads mit langen, wiederkehrenden Prefixen (RAG mit gleichem Kontext, Multi-Turn-Chatbot mit gleichem System-Prompt) ist die Throughput-Verbesserung messbar.
Auf der Cloud-API-Seite implementieren Anbieter eine analoge Funktion: Automatisches Prompt-Caching reduziert die Kosten für Eingabe-Token bei wiederholten Prefixen um grob 50–90 %. Das ist auch für hybride Architekturen relevant, bei denen manche Requests in die Cloud gehen — eine saubere Prompt-Struktur (konstanter System-Prompt vorne, dynamischer Inhalt hinten) kann die Rechnung spürbar reduzieren. Ausführlich behandelt das der Artikel Prompt-Caching und Kosten.
Wie Sie mehr aus einer GPU herausholen — ohne neue Hardware
Zusammenfassung der praktischen Stellschrauben, die wir in Deployments sehen — sortiert nach typischer Wirkung:
- 1.Wechseln Sie auf ein produktionsfähiges Serving-Framework — wenn Sie
Ollamamit mehreren gleichzeitigen Nutzern betreiben, ist der Wechsel aufvLLModerSGLangdie wirkungsvollste Einzelmaßnahme. Continuous Batching und PagedAttention sind dort bereits integriert.
- 1.Setzen Sie die richtige Quantisierung ein — Q4_K_M oder AWQ 4-bit reduziert den Speicher-Footprint des Modells gegenüber FP16 deutlich (typischerweise auf ein Drittel bis ein Viertel), was VRAM für größere Batches freimacht — bei einem Qualitätsverlust unter 5–8 %. Mehr zu den Formaten im Artikel LLM-Quantisierung (GGUF, AWQ, GPTQ).
- 1.Aktivieren Sie KV-Cache-Quantisierung — FP8- oder INT8-KV-Cache halbiert den Speicher-Footprint bei minimalem Einfluss auf die Ausgaben. In
vLLMist das der Parameter--kv-cache-dtype.
- 1.Optimieren Sie für Ihren Kontext — wenn Ihre Requests im Durchschnitt nur 20 % des eingestellten maximalen Kontexts ausnutzen, gibt das Absenken von
--max-model-lenVRAM für mehr parallele Requests frei.
- 1.Nutzen Sie Prefix-Caching — wenn System-Prompt oder RAG-Kontext über Requests hinweg identisch sind, leiten Sie diese an ein Framework mit RadixAttention (SGLang) oder aktivieren Sie Prefix-Caching in
vLLM.
- 1.Messen Sie die tatsächliche GPU-Auslastung —
nvidia-smi dmonund die Metriken des Serving-Frameworks zeigen, wo der Bottleneck liegt. Niedrige rechnerische GPU-Auslastung bei hoher Latenz signalisiert typischerweise ein Problem mit der KV-Cache-Verwaltung oder suboptimales Batching.
Wann mehrere GPUs sinnvoll sind
Horizontale Skalierung (Tensor-Parallelismus über mehrere GPUs) ist in zwei Situationen gerechtfertigt: Das Modell passt selbst nach Quantisierung nicht mehr auf eine einzelne GPU, oder Sie haben alle Optimierungen auf einer GPU ausgeschöpft und der Throughput reicht noch immer nicht.
Tensor-Parallelismus (--tensor-parallel-size 2 in vLLM) teilt die Modellmatrizen auf die GPUs auf — jede GPU übernimmt einen Teil der Berechnung, die Ergebnisse werden synchronisiert. Er skaliert für die Prefill-Phase nahezu linear, für Decode weniger effizient (wegen Synchronisations-Overhead).
Für die meisten Unternehmens-Deployments mit einem Modell und Dutzenden gleichzeitiger Nutzer ist eine gut konfigurierte einzelne GPU mit dem richtigen Serving-Framework leistungsfähiger und wirtschaftlicher als zwei GPUs mit Ollama. Hardware zu kaufen, bevor die Software optimiert ist, ist ein verbreiteter, aber unnötig teurer Fehler.
Für die Frage, welche GPU konkret zu wählen ist und wie viel VRAM Sie für ein gegebenes Modell und eine gegebene Last benötigen, verweisen wir auf den praktischen Entscheidungsrahmen im Artikel Welche GPU für LLM-Inferenz.
Häufige Fragen
Was ist TTFT und warum ist es wichtig?
TTFT (Time to First Token) ist die Zeit vom Absenden des Requests bis der Server beginnt, die ersten Token der Antwort zu streamen. Für interaktive Anwendungen (Chatbots, Copilots) ist TTFT entscheidend für die wahrgenommene Geschwindigkeit — ein Nutzer, der den ersten Token innerhalb von 1–2 Sekunden erhält, nimmt das System als responsiv wahr, auch wenn die vollständige Antwort 10 Sekunden dauert. Langer Kontext und ein voller KV-Cache verlängern den TTFT, weil die Prefill-Phase mehr Zeit benötigt.
Was ist der Unterschied zwischen PagedAttention und Continuous Batching?
Es sind zwei orthogonale Optimierungen, die unterschiedliche Probleme lösen. PagedAttention löst die Speicherverwaltung — es reduziert die KV-Cache-Fragmentierung, indem es Speicher dynamisch in Seiten allokiert statt ihn vorab zu reservieren. Continuous Batching löst das Request-Scheduling — anstatt auf das Ende eines Batches zu warten, werden neue Requests laufend in den aktuellen Durchlauf aufgenommen. Beide wirken zusammen und sind in produktiven Frameworks wie vLLM implementiert.
Lohnt sich Prefix-Caching auch für kleinere Deployments?
Ja, sofern Sie einen konsistenten System-Prompt oder RAG-Kontext haben, der sich über Requests wiederholt. Selbst bei einem Dutzend gleichzeitiger Nutzer kann Prefix-Caching den TTFT für Requests mit langem gecachten Prefix um 40–70 % senken. Auf der Cloud-API-Seite wirkt sich das direkt auf die Kosten aus — ein sauber strukturierter Prompt mit konstantem Prefix kann Dutzende Prozent bei Eingabe-Tokens einsparen.
Wann sollte man von Ollama auf vLLM wechseln?
Sobald mehr als ein gleichzeitiger Nutzer in einem Produktionsumfeld vorhanden ist. Ollama ist hervorragend für den Developer-Desktop, Prototyping und Single-User-Lokal-Betrieb. Bei mehreren parallelen Requests liefern Continuous Batching und PagedAttention in vLLM bei gleicher Hardware deutlich höheren Throughput. Der Wechsel ist vergleichsweise einfach — vLLM bietet ein OpenAI-kompatibles API, sodass in der Regel eine URL- und API-Key-Änderung ausreicht.
Wie beeinflusst die Kontextlänge den Throughput?
Linear und erheblich. Längerer Kontext bedeutet mehr KV-Cache pro Request, was direkt die Anzahl der Requests reduziert, die gleichzeitig in den verfügbaren VRAM passen. Ein Modell mit 1M-Kontextfenster benötigt für einen einzelnen langen Request grob im Bereich von Hunderten von Gigabyte KV-Cache — für übliche Produktions-GPUs nicht erreichbar. Für die meisten realen Use-Cases ist RAG mit kürzerem Kontext wirtschaftlich deutlich vorteilhafter als ein langes Kontextfenster, das mit einem vollständigen Dokument befüllt wird. Mehr zur Entscheidung zwischen RAG und langem Kontext im Artikel Kontextfenster — wann 1M Token helfen.
*MP Industrial Solutions unterstützt Unternehmen dabei, eine LLM-Serving-Architektur zu entwerfen, die zur Last und zum Budget passt — von der Wahl des Serving-Frameworks bis zur Konfiguration von KV-Cache und Quantisierung. Wenn Sie eine Verlangsamung im bestehenden Deployment beheben oder einen Produktions-Rollout planen, analysieren wir gerne die konkreten Zahlen und erarbeiten eine Optimierungsstrategie.*
