Jooksupikkuskodeerimine (RLE)

Sisesta suvaline tekst ja vaata, kuidas see jaguneb kordusjadadeks — sama tähemärgi järjestikused kordused sulanduvad üheks (sümbol, arv) paariks. Pikad kordusjadad kahandavad andmeid; lühikesed kordusjadad kasvatavad neid.

Interaktiivse simulatsiooni laadimine...

Õppetund

Teooria — Jooksupikkuskodeerimine (RLE)

Jadapikkuskodeerimine asendab iga maksimaalse ühesuguste sümbolite jada ühe paariga (sümbol, arv). Näidikule ei jõua tekst, vaid kaks arvu: N märki ja R jada. Kõik ülejäänud arvud lehel on nende kahe jagatis.

Mida iga sümbol tähendab

N
sisendmärkide arv — see, kui pikk on sinu kirjutatu, ei muud.
R
jadade arv, see tähendab ühe korduva sümboli maksimaalsete plokkide arv. R kasvab ühe võrra igal pool, kus kaks naabrit erinevad: loetakse piire, mitte märke.
N/R, keskmine jada pikkus. See ongi ainus suurus, mis tulemuse otsustab.
ratio
N/2R, see tähendab L̄/2. Üle 1 on väljund sisendist väiksem.

Kust valem tuleb

  1. Loe jadasid, mitte märke. Stringis 0010111100001111 erinevad naabrid viies kohas, seega on kuus jada ja rida näitab R=6.
  2. Kodeeritud suurus on 2R ja ei midagi muud. Millest jadad koosnevad, ei jõua arvutusse kunagi — kuus jada maksavad kaksteist ühikut, olgu need pikslid, tähed või numbrid.
  3. Jaga: ratio = N/2R = L̄/2. Tasakaalupunkt on seega L̄ = 2 ja see on täpselt saavutatav — kirjuta AABB ja tulbad näitavad 4 baiti sisse, 4 baiti välja.
  4. Kaks suunda ei ole sümmeetrilised. Ülespoole piiri ei ole: üksainus miljoni märgi pikkune jada kodeerub üheks paariks. Allapoole on põrand 0.50× ja sellest madalamale ei saa, sest halvim, mida sisend teha suudab, on anda igale märgile oma jada.

Kuidas nähtut lugeda

Kõik neli näidet on täpselt kuusteist märki pikad, mistõttu tasub neid lugeda ühe komplektina. Pildirida annab kolm jada ja 6 baiti. Klassikalised jadad annab neli ja 8. Bitimask annab kuus ja 12. Halvim juht annab kuusteist ja 32. Sisse sama pikkus, välja 6 kuni 32 baiti — viiekordne vahe, mille otsustab üksnes R. Kirjuta siis hello world: üksteist märki, kümme jada, 20 baiti. Tavaline tekst asub selle vahemiku alumises otsas, ja just seepärast on jadapikkuskodeerimine kompressorite osa, mitte kompressor omaette.

Eeldab
Et paar maksab täpselt 2 ühikut, et sümbol ja arv on ühelaiused ning et arv võib olla kui tahes suur. Päris kodeerijad annavad arvule kindla laiuse — ühe baidi, seega 255 — ja peavad pikema jada mitmeks paariks murdma, mis tõstab tasakaalupunkti veidi üle 2. Ühelaiuse eeldus kukub kõige selgemalt läbi just seal, kus see meetod on parim: 1-bitises faksis on sümbol üks bitt, arv aga mitte.
Ei kehti, kui
Põrand 0.50× ei ole viga, mida annaks välja projekteerida. Kadudeta kodeerija peab olema pööratav, nii et erinevad sisendid annaksid erinevad väljundid; lühikesi sõnesid, kuhu kujutada, on aga vähem kui pikki. Iga skeem, mis lühendab kas või ühte sisendit, pikendab seetõttu mõnda teist. See on loendamisfakt, mitte jadapikkuskodeerimise omadus. PackBits kolmandas ülaltoodud tähelepanekus surub oma halvima juhu ühele juhtbaidile 128 kohta — alla 1% — ja kaugemale ei jõua keegi, sest põrandat saab lõputult alandada, kuid mitte kunagi saavutada. See meetod lihtsalt kannab seda kulu väljaspool, näidikul, mille liikumist saab jälgida.

miks tasakaalupunkt on täpselt 2 🖖

Iga kordusjada — sõltumata pikkusest — maksab salvestamisel sama palju: 2 ühikut, üks sümboli, üks arvu jaoks. Pikkusega L kordusjada tasub kodeerida ainult siis, kui see maksab vähem kui L toormärgi väljakirjutamine — see tähendab, kui L on suurem kui 2. Kogu sisendi peale keskmistatuna muutub see tingimuseks L̄ = N/R suurem kui 2, kus N on kogupikkus ja R kordusjadade arv — täpselt see joon, mida ülaltoodud valem kontrollib. Seepärast on RLE ka nõrk üldotstarbeline kompressor: inglise tekstis, lähtekoodis ja juhuslikes andmetes on kordusjadad harva pikemad kui 2, mistõttu RLE on jäetud andmetele, mis on tahtlikult loodud pikkade kordusjadadega — 1-bitised faksiskaneeringud, hõredad bittkaardid ja paletiga pildid ühevärviliste aladega. Päris formaadid viivad idee kaugemale: PNG rakendab enne tihendamist igal skaneerimisreal Paeth/Sub/Up deltafiltrit, muutes esmalt sujuvad üleminekud pikkadeks peaaegu-nulliliste erinevuste kordusjadadeks — RLE (DEFLATE'i kaudu) teeb ülejäänu. Proovi ülaltoodud halvima juhu näidet: kuusteist erinevat tähemärki annavad kuusteist pikkusega 1 kordusjada, seega vajab kodeerimine 16 tähemärgi salvestamiseks 32 ühikut — sisend kahekordistub.

pakkimine, mille leiutaksid ise 🖖

Jadapikkuskodeerimine (RLE) on ainus pakkimisidee, mille võiksid ise välja mõelda: selle asemel et kirjutada WWWWWWW täht-tähelt välja, ütled lihtsalt "7 W" — sama otsetee, mida inimesed kasutavad, öeldes telefoninumbris "kolm seitset". See läbib andmed ühe vasakult paremale käiguga ega mäleta midagi peale parasjagu loendatava jada, mistõttu on see kiire ja hõlpsasti voogedastatav. Ja see on kadudeta: paaridest (sümbol, arv) saad algandmed täpselt taastada — erinevalt JPEG-ist või MP3-st, mis loobuvad detailidest jäädavalt.

RLE sugulane, mis ei paisu 🖖

Naiivne RLE võib pakkimatuid andmeid kahekordistada, kuid Apple'i variant PackBits — sündinud 1980ndate MacPaintis ja tänini TIFF-i standardne pakkimisrežiim — on ehitatud nii, et see peaaegu kunagi ei kasva. Iga plokk algab ühe märgiga juhtbaidiga: mittenegatiivne väärtus tähendab "järgnevad baidid on sõnasõnalised", negatiivne "korda järgnevat baiti". Unikaalsed andmed kopeeritakse muutmata kujul kuni 128-baidistes plokkides, nii et halvimal juhul lisandub vaid üks juhtbait 128 kohta — alla 1% lisakulu, mitte 100%, milleni naiivne RLE võib küündida.

Ülesanne täielikult lahendatud

  1. AAAAAABBBCCDDDDD käigupikkuse kodeerimine neljaks paariks 5 sammu

    Käituskodeerimine teisendab jada AAAAAABBBCCDDDDD neljaks paariks. Arvuta välja tihendusaste ja seejärel täpne tingimus, mille korral see skeem muudab faili suuremaks.

    1. Kodeering on ilmselge: asenda iga seeria märgiga ja selle pikkusega. Kuusteist märki koondub neljaks paariks.

    2. Selle skeemi mis tahes sisendit kirjeldavad kaks arvu — selle pikkus ja seeriate arv — ning nende suhe on seeria keskmine pikkus. Siin on see 4.

    3. Nüüd loenda ausalt. Iga paar maksab kaks sümbolit, ühe märgi ja ühe arvu, seega on väljund 2R sisendi N vastu. Miski muu andmete juures ei loe.

    4. Skeem annab seega võidu täpselt siis, kui 2R < N, mis teiseneb tingimuseks, et seeria keskmine pikkus on üle 2. Siin 8 vastu 16 — puhas pooleks tegemine — ja otsuselida paneelil ütleb sama asja ühe sümboliga.

    5. Sellest künnisest allpool see kaotab ning kui seeria keskmine pikkus on 1, kaotab see maksimaalselt: iga märk muutub paariks, dubleerides faili suuruse.

    Vastus

    Tööriist kuvab N = 16 ja R = 4, seeria keskmiseks pikkuseks 4 ja võiduks 2×. See tingimus ongi peaasi: RLE tihendab parajasti siis, kui seeriate keskmine pikkus on üle kahe, ning see on üks väheseid tihendusskeeme, mille tasakaalupunkt on üksainus silmaga kontrollitav arv. Kirjuta kasti ABCD ja vaata, kuidas see paisub kahekordseks. See pole puudus — seetõttu püsib RLE kasutusel vaid seal, kus seeriad on ehituslikult tagatud: faksi skaneerimisridadel, hõredatel bittkaartidel ja JPEG lamedatel aladel pärast kvantimist, mitte kunagi tavatekstis.

Õpitee

Käsitsi tihendamine

Viib edasi Huffman põhiidee selle kõige puhtamal kujul: asendada identsete sümbolite jada vastava märgi ja korduste arvuga.

Allikad (3)

Näiteülesanded

  • Klassikalised kordusjadad - "AAAAAABBBCCDDDDD" → (A,6)(B,3)(C,2)(D,5) — 16 tähemärki muutub 8 paariks
  • Halvim juht - "ABCDEFGHIJKLMNOP" — kõik tähemärgid unikaalsed, iga paar on originaalist pikem
  • Bittkaardi mask - "0010111100001111" — pikslirida, mis näitab, miks PNG rakendab enne RLE-d eelfiltrit
  • Pildi skaneerimisrida - "WWWWWWWBBBBBWWWW" — lihtne must-valge pildirida, tugev korduste struktuur