Lauflängenkodierung (RLE)

Gib beliebigen Text ein und beobachte, wie er in Läufe zerlegt wird — aufeinanderfolgende Wiederholungen desselben Zeichens verschmelzen zu einem einzigen (Symbol, Anzahl)-Paar. Lange Läufe verkleinern die Daten, kurze Läufe vergrößern sie.

Interaktive Simulation wird geladen...

Lektion

Die Theorie — Lauflängenkodierung (RLE)

Die Lauflängenkodierung ersetzt jeden maximalen Lauf gleicher Symbole durch ein einziges Paar (Symbol, Anzahl). In der Anzeige landet nicht der Text, sondern zwei Zahlen: N Zeichen und R Läufe. Jede weitere Größe auf der Seite ist der Quotient dieser beiden.

Was die einzelnen Symbole bedeuten

N
die Zahl der eingehenden Zeichen — die Länge des Getippten, mehr nicht.
R
die Zahl der Läufe, also maximaler Blöcke eines wiederholten Symbols. R steigt überall dort um eins, wo sich zwei Nachbarn unterscheiden; gezählt werden Grenzen, nicht Zeichen.
N/R, die mittlere Lauflänge. Sie allein entscheidet über das Ergebnis.
ratio
N/2R, also L̄/2. Über 1 ist die Ausgabe kleiner als die Eingabe.

Woher die Formel kommt

  1. Zähle Läufe, nicht Zeichen. In 0010111100001111 unterscheiden sich die Nachbarn an fünf Stellen, also gibt es sechs Läufe und die Zeile zeigt R=6.
  2. Die kodierte Größe ist 2R und sonst nichts. Woraus die Läufe bestehen, geht nie in die Rechnung ein — sechs Läufe kosten zwölf Einheiten, ob es Pixel, Buchstaben oder Ziffern sind.
  3. Teile: ratio = N/2R = L̄/2. Die Nulllinie liegt damit bei L̄ = 2, und sie ist exakt erreichbar — tippe AABB, und die Balken zeigen 4 Bytes hinein, 4 Bytes hinaus.
  4. Die beiden Richtungen sind nicht symmetrisch. Nach oben gibt es keine Grenze: ein einzelner Lauf von einer Million Zeichen wird zu einem Paar. Nach unten liegt der Boden bei 0.50× und ist nicht zu unterbieten, denn schlimmer als ein eigener Lauf je Zeichen geht es nicht.

So liest du, was du siehst

Alle vier Beispiele sind genau sechzehn Zeichen lang — deshalb lohnt es sich, sie als Satz zu lesen. Bildzeile hat drei Läufe und ergibt 6 Bytes. Klassische Läufe hat vier und ergibt 8. Bitmaske hat sechs und ergibt 12. Schlechtester Fall hat sechzehn und ergibt 32. Gleiche Länge hinein, und heraus kommt zwischen 6 und 32 Bytes — Faktor fünf, allein durch R entschieden. Tippe dann hello world: elf Zeichen, zehn Läufe, 20 Bytes. Gewöhnlicher Fließtext liegt am unteren Ende dieser Spanne, und genau deshalb ist RLE ein Bauteil von Kompressoren und keiner für sich.

Setzt voraus
Dass ein Paar genau 2 Einheiten kostet, dass Symbol und Anzahl gleich breit sind und dass eine Anzahl beliebig groß sein darf. Echte Kodierer geben der Anzahl eine feste Breite — ein Byte, also 255 — und müssen längere Läufe in mehrere Paare zerlegen, was die Nulllinie etwas über 2 schiebt. Die Gleichbreiten-Annahme scheitert am deutlichsten genau dort, wo RLE am besten ist: in einem 1-Bit-Faxscan ist das Symbol ein Bit, die Anzahl nicht.
Versagt, wenn
Der Boden bei 0.50× ist kein Mangel, den man wegkonstruieren könnte. Ein verlustfreier Kodierer muss umkehrbar sein, verschiedene Eingaben also auf verschiedene Ausgaben abbilden; und es gibt weniger kurze Zeichenfolgen als lange, auf die abgebildet werden könnte. Jedes Verfahren, das auch nur eine Eingabe verkürzt, verlängert daher eine andere. Das ist eine Abzählaussage, keine Eigenschaft der Lauflängenkodierung. PackBits im dritten Einblick oben drückt seinen schlechtesten Fall auf ein Steuerbyte je 128 — unter 1% — und weiter kommt niemand, denn der Boden lässt sich beliebig senken, aber nie erreichen. RLE trägt diese Kosten nur außen, in einer Anzeige, der man beim Wandern zusehen kann.

warum der Break-even-Punkt genau 2 ist 🖖

Jeder Lauf — egal wie lang — kostet gleich viel zum Speichern: 2 Einheiten, eine für das Symbol, eine für die Anzahl. Ein Lauf der Länge L lohnt sich nur, wenn das weniger kostet als L Rohzeichen auszuschreiben — also wenn L größer als 2 ist. Über die gesamte Eingabe gemittelt wird daraus L̄ = N/R größer als 2, wobei N die Gesamtlänge und R die Anzahl der Läufe ist — genau die Bedingung, die die Formel oben prüft. Das erklärt auch, warum RLE ein schlechter allgemeiner Kompressor ist: englischer Text, Quellcode und Zufallsdaten haben selten Läufe länger als 2, weshalb RLE Daten vorbehalten bleibt, die absichtlich lange Läufe erzeugen — 1-Bit-Faxscans, dünn besetzte Bitmaps und Palettenbilder mit einfarbigen Flächen. Reale Formate treiben das weiter: PNG wendet vor der Kompression einen Paeth-/Sub-/Up-Deltafilter auf jede Scanzeile an, der weiche Farbverläufe zuerst in lange Läufe von Differenzen nahe null verwandelt — RLE (über DEFLATE) erledigt den Rest. Probiere oben das Worst-Case-Beispiel: sechzehn verschiedene Zeichen ergeben sechzehn Läufe der Länge 1, sodass die Kodierung 32 Einheiten für 16 Zeichen braucht — die Eingabe verdoppelt sich.

Kompression, die man selbst erfinden würde 🖖

Lauflängenkodierung ist die eine Kompressionsidee, auf die man von allein käme: Statt WWWWWWW Zeichen für Zeichen auszuschreiben, sagt man einfach "7 W" — genau die Abkürzung, die Menschen bei einer Telefonnummer als "dreimal die Sieben" nutzen. Sie durchläuft die Daten in einem einzigen Durchgang von links nach rechts und merkt sich nichts außer dem gerade gezählten Lauf, was sie schnell und gut streambar macht. Und sie ist verlustfrei: Aus den (Symbol, Anzahl)-Paaren lässt sich das Original exakt rekonstruieren — anders als bei JPEG oder MP3, die Details für immer verwerfen.

der RLE-Verwandte, der nicht platzt 🖖

Naive RLE kann inkomprimierbare Daten verdoppeln, doch Apples Variante PackBits — entstanden im MacPaint der 1980er und bis heute ein Standard-Kompressionsmodus in TIFF — ist so konstruiert, dass sie fast nie wächst. Jeder Block beginnt mit einem vorzeichenbehafteten Steuerbyte: ein nicht-negativer Wert bedeutet "die nächsten Bytes sind wörtlich", ein negativer "wiederhole das folgende Byte". Einzigartige Daten werden in Blöcken von bis zu 128 Bytes unverändert kopiert, sodass der schlimmste Fall nur ein Steuerbyte pro 128 hinzufügt — unter 1 % Mehraufwand statt der 100 %, die naive RLE erreichen kann.

Aufgabe vollständig gelöst

  1. Lauflängenkodierung von AAAAAABBBCCDDDDD in vier Paare 5 Schritte

    Die Lauflängenkodierung macht aus AAAAAABBBCCDDDDD vier Paare. Berechnen Sie die Kompression und anschließend die genaue Bedingung, unter der dieses Verfahren eine Datei größer macht.

    1. Die Kodierung ist die offensichtliche: Jeder Lauf wird durch das Zeichen und seine Länge ersetzt. Sechzehn Zeichen schrumpfen zu vier Paaren.

    2. Zwei Zahlen beschreiben jede Eingabe für dieses Verfahren — ihre Länge und ihre Anzahl an Läufen — und ihr Verhältnis ist die mittlere Lauflänge. Hier beträgt sie 4.

    3. Nun zählen wir ehrlich nach. Jedes Paar kostet zwei Token, ein Zeichen und eine Anzahl, sodass die Ausgabe 2R gegenüber einer Eingabe von N beträgt. Nichts anderes an den Daten spielt eine Rolle.

    4. Das Verfahren gewinnt also genau dann, wenn 2R < N gilt, was umgeformt eine mittlere Lauflänge von über 2 ergibt. Hier steht 8 gegen 16 — eine saubere Halbierung — und die Ergebniszeile auf dem Panel drückt mit einem einzigen Symbol dasselbe aus.

    5. Unterhalb dieser Schwelle verliert es, und bei einer mittleren Lauflänge von 1 verliert es maximal: Jedes Zeichen wird zu einem Paar, was die Datei verdoppelt.

    Antwort

    Das Werkzeug gibt N = 16 und R = 4 aus, eine mittlere Lauflänge von 4 und eine 2× Ersparnis. Diese Bedingung gilt es festzuhalten: RLE komprimiert genau dann, wenn die Läufe im Schnitt mehr als zwei betragen, und es ist eines der wenigen Kompressionsverfahren, dessen Gewinnschwelle eine einzelne Zahl ist, die man auf einen Blick prüfen kann. Geben Sie ABCD in das Feld ein und beobachten Sie, wie es auf die doppelte Größe anwächst. Das ist kein Mangel — es ist der Grund, warum RLE nur dort überlebt, wo Läufe konstruktionsbedingt garantiert sind: Fax-Abtastzeilen, dünnbesetzte Bitmaps und die flachen Bereiche eines JPEG nach der Quantisierung, niemals bei allgemeinem Text.

Lernpfad

Kompression von Hand

Führt zu Huffman die Idee in ihrer einfachsten Form: Ersetze eine Folge gleicher Symbole durch das Symbol und eine Anzahl.

Quellen (3)

Beispielaufgaben

  • Klassische Läufe - "AAAAAABBBCCDDDDD" → (A,6)(B,3)(C,2)(D,5) — 16 Zeichen werden zu 8 Paaren
  • Worst Case - "ABCDEFGHIJKLMNOP" — alle Zeichen einzigartig, jedes Paar ist länger als das Original
  • Bitmap-Maske - "0010111100001111" — Pixelzeile, die zeigt, warum PNG vor RLE vorfiltert
  • Bild-Scanzeile - "WWWWWWWBBBBBWWWW" — einfache Schwarz-Weiß-Bildzeile mit starker Laufstruktur