Selaimen muistirajat tiedostoja käsiteltäessä
Tiedostoni on vain 15 MB. Miksi välilehden muisti loppui?
Levyllä oleva tiedosto on pakattu versio
Koko väärinkäsitys yhdessä lauseessa: tiedostonhallinnassa näkyvä luku on pakatun datan koko, eikä mitään voi käsitellä niin kauan kuin se on pakattuna. Kuvan skaalaaminen, uudelleenpakkaus, muuntaminen tai analysointi vaatii, että se puretaan ensin raakapikseleiksi, ja raakapikselit ovat valtavia.
Laskutoimitus on yksinkertainen. Pikseli muistissa on tavallisesti neljä tavua – punainen, vihreä, sininen ja alfa. 4000 × 3000 -valokuvassa on kaksitoista miljoonaa pikseliä, joten purettu bittikartta on noin 48 MB. JPEG, josta se tuli, saattoi olla 4 MB. Tiedosto kasvoi kaksitoistakertaiseksi ennen kuin mitään työtä oli aloitettu.
| Mitat | Pikselit | Purettu bittikartta |
|---|---|---|
| 1920 × 1080 | 2,1 miljoonaa | noin 8 MB |
| 4000 × 3000 | 12 miljoonaa | noin 48 MB |
| 6000 × 4000 | 24 miljoonaa | noin 96 MB |
| 10000 × 10000 | 100 miljoonaa | noin 400 MB |
Eikä yksi kopio koskaan riitä
Realistinen käsittelyketju pitää muistissa useaa kopiota kerralla: pakatut syötetavut, puretun lähdebittikartan, uusiin mittoihin skaalatun tulosbittikartan, enkooderin sisäiset puskurit ja pakatun tuloksen. Työkalu, joka näyttää lisäksi esikatselun, pitää vielä yhtä. Yllä olevalle 4000 × 3000 -valokuvalle kahden tai kolmensadan megatavun huippumuistinkäyttö on täysin tavallista – tiedostolle, joka näytti 4 MB:n kokoiselta.
PDF:n rasterointi käyttäytyy samoin, sivu kerrallaan: 300 DPI:llä renderöity A4-sivu on noin 2480 × 3508 pikseliä eli purettuna noin 35 MB, ja työkalu joka renderöi useita sivuja kerralla kertoo tuon luvun. Video on vielä pahempi, koska dekooderi tarvitsee useita vertailuruutuja muistiin samanaikaisesti.
Missä todelliset katot ovat
- Välilehden muistibudjetin asettaa selain, ei sivusto, ja se on pienempi kuin koneen asennettu muisti. Se myös kutistuu, kun muilla välilehdillä on työtä.
- Yleisen 32-bittisen muistimallin mukaan käännetyt WebAssembly-moduulit voivat osoittaa enintään neljä gibitavua, ja selaimet sallivat instanssia kohti usein huomattavasti vähemmän.
- Yksittäisillä puskureilla on oma enimmäispituutensa, joka on selvästi alle sen kokonaismuistin, jota sivu saa käyttää.
- Mobiilikäyttöjärjestelmät lopettavat liian suureksi kasvavan välilehden ilman varoitusta ja ilman virhettä, jonka sivu voisi napata kiinni.
- Näytönohjaimen muisti on erillinen, pienempi varanto. Alustan enimmäismitat ylittävä canvas yksinkertaisesti epäonnistuu, olipa järjestelmämuistia vapaana kuinka paljon tahansa.
Mitään näistä ei julkaista yhtenä lukuna, jonka voisi tarkistaa, koska ne riippuvat selaimesta, versiosta, laitteesta ja siitä mitä muuta on käynnissä. Siinä on todellinen vaikeus: työkalu ei voi kysyä, paljonko muistia se saa käyttää.
Miksi puhelimet ovat tiukin tapaus
Puhelimissa on vähemmän fyysistä muistia, ei työpöytäkoneiden tapaista sivutusta ja käyttöjärjestelmä, joka ottaa muistia taustaprosesseilta armottomasti takaisin. Selaimen välilehti on taustaprosessi sillä hetkellä kun vastaat viestiin. Siksi mobiiliselaimissa on tiukemmat budjetit ja ne hylkäävät välilehden nopeammin, ja hylkäys näyttää sinulle yleensä siltä että sivu latautuu uudelleen ja työsi katoaa, ei virheeltä.
Käytännön seuraus on, että työ joka valmistuu läppärillä voi olla mahdoton puhelimessa samalla tiedostolla. Se ei ole vika työkalussa. Se on laitteistoraja, ja rehellinen vastaus on sanoa se ennen aloittamista eikä kaatua puolimatkassa.
Miten huolellinen työkalu käyttäytyy
- Se arvioi muistintarpeen purettujen mittojen perusteella ennen kuin varaa mitään, ja kieltäytyy työstä joka selvästi ei mahdu.
- Se käsittelee rajallisella laitteella yhden tiedoston kerrallaan sen sijaan että ajaisi erän rinnakkain.
- Se siirtää puskurit sivun ja sen workereiden välillä kopioimisen sijaan, joten suuri tiedosto ei ole olemassa kahteen kertaan.
- Se vapauttaa jokaisen tuloksen heti kun se on kirjoitettu, ja mitätöi väliaikaiset URL-osoitteet, jotka muuten pitäisivät datan hengissä.
- Se käsittelee virtana sivu sivulta tai ruutu ruudulta silloin kun muoto sen sallii, sen sijaan että lataisi koko asiakirjan muistiin.
- Se rajaa hyväksymänsä pikselimäärän, mikä on myös se, mikä estää valtavaksi canvasiksi laajenevaa pientä tiedostoa kaatamasta välilehteä.
Mitä voit tehdä, kun työ epäonnistuu
- Sulje muut välilehdet. Ne kilpailevat samasta budjetista, eivätkä selaimet jaa sitä reilusti.
- Käsittele vähemmän tiedostoja kerralla. Yhden mittainen jono on hitaampi ja valmistuu paljon todennäköisemmin.
- Pienennä ensin mittoja. Pisimmän sivun puolittaminen neljännestää muistintarpeen, ja se on usein muutenkin se mitä halusit.
- Jaa suuri PDF osiin ja käsittele osat.
- Siirry työpöytäkoneelle suurimpia töitä varten. Tämä ei ole paikallisen käsittelyn epäonnistuminen, vaan käytettävissä olevan laitteiston oikeaa käyttöä.
- Käynnistä selain uudelleen, jos välilehti on ollut auki päiviä. Pitkään auki olleisiin välilehtiin kertyy muistia, jonka uudelleenlataus vapauttaa.
Jokaisen arvion raja
Selaimet paljastavat käytettävissä olevasta muistista vain karkean vihjeen, ja jotkin eivät paljasta mitään. Mikä tahansa luku, jonka paikallinen työkalu näyttää, on siis arvio, joka on rakennettu tiedoston omista mitoista ja varovaisesta mallista käsittelyketjusta, ei lukema käyttöjärjestelmältä. Se on hyödyllinen sen päättämiseen, kannattaako työtä yrittää. Se ei ole lupaus siitä, että työ valmistuu, koska ratkaiseva tekijä – se mitä muu laite tekee seuraavien kolmenkymmenen sekunnin aikana – ei ole verkkosivun nähtävissä.
Työkalut tähän
Lähteet
- W3C — WebAssembly Core Specification, memory model
- W3C — Device Memory API, and why the value is coarse
- WHATWG — HTML Standard, transferable objects