Přejít k navigační liště

Zdroják » JavaScript » Do hlubin implementací JavaScriptu: 1. díl – úvod

Do hlubin implementací JavaScriptu: 1. díl – úvod

Články JavaScript, Různé

Tento článek otevírá nový seriál, který bude věnován implementacím JavaScriptu. Postupně si v něm představíme nejdůležitější současné interprety tohoto jazyka (především ty obsažené ve webových prohlížečích) a u některých vybraných se podrobněji podíváme, jak vypadají uvnitř. Nejvíc nás přitom bude zajímat, jaké techniky se v nich používají pro optimalizaci a urychlení spouštěného kódu.

Seriál je určen primárně pro zvídavé webové vývojáře pracující s JavaScriptem. Pro ty, které zajímá, jak všechno funguje pod povrchem, ale sami nikdy nenašli sílu či čas implementace JavaScriptu zkoumat. V průběhu seriálu budeme tedy předpokládat, že čtenář JavaScript v praxi používá a dobře zná, nebudeme ale předpokládat nic navíc. Není potřeba mít za sebou přednášku z tvorby kompilátorů apod. – všechny implementační techniky a pojmy budou vysvětleny. Předpokladům o čtenáři bude odpovídat také hloubka, do jaké budou jednotlivé oblasti probírány, a technická náročnost.

Proč toto téma a proč právě teď?

Historie

Pro plné pochopení, proč je právě v této době zajímavé se zabývat implementacemi JavaScriptu, je třeba se podívat do historie.

První verze JavaScriptu se objevila v roce 1995 v prohlížeči Netscape Navigator 2. JavaScript byl tehdy zamýšlen jako nástroj na doplnění jednoduchých dynamických prvků do webových stránek. Jeho typické použití byly validace formulářů na straně klienta a drobné efekty s obrázky – o moc víc s tehdejším JavaScriptem dělat nešlo. Programy v JavaScriptu tak měly většinou délku jen několika řádků.

Situace se změnila s příchodem Internet Exploreru 4, který jako první prohlížeč umožnil skriptům přistupovat k objektovému modelu celé stránky. Z JavaScriptu se tak dal měnit obsah libovolných částí stránky, přidávat obsah nový či naopak obsah mazat. Možnosti JavaScriptu se tím řádově rozšířily, objevila se spousta skriptů typu „moje super vyskakovací menu“ a průměrná délka skriptů ve stránkách podstatně vzrostla.

Dalším zlomem byl nástup AJAXu, který umožňoval stránkám komunikovat se serverem a zobrazovat uživateli nový obsah či provádět různé akce, aniž by bylo nutné nové načtení stránky. Pamětníci vědí, jaký poprask způsobilo uvedení GMailu – první aplikace, která byla na JavaScriptu a AJAXu kompletně postavená a nemohla bez nich fungovat. Takových aplikací je dnes mnoho a jejich společným rysem je, že obsahují stovky kB javascriptové­ho kódu.

Posledním důležitým bodem ve vývoji JavaScriptu byl nástup knihoven typu Prototype a jQuery. Jejich cílem je usnadnit práci s DOM a skrýt některé rozdíly mezi prohlížeči. Důsledkem je, že prakticky každá nová stránka si dnes s sebou nese desítky kB JavaScriptového kódu a při běžných operacích se vykoná více javascriptových příkazů, než tomu bylo bez knihoven.

Z předchozích odstavců je vidět jednoznačný trend – důležitost JavaScriptu, jeho složitost a množství obsažené ve webových stránkách postupně rostlo, a to o několik řádů. Naproti tomu implementace v prohlížečích zůstávaly po mnoho let prakticky nezměněné, když pomineme přidávání nových vlastností a občasnou příležitostnou optimalizaci.

Současnost

V posledním cca roce se ale situace změnila. Výrobci prohlížečů si začali uvědomovat, že javascriptové interprety se stávají úzkým hrdlem mnohých webových aplikací a v nejednom případě jsou hlavní příčinou jejich pomalosti. Začali na rychlosti JavaScriptu intenzivně pracovat a vše se postupně vyhrotilo až do podoby závodu (především mezi prohlížeči Firefox a Safari), kdy se jednotlivé strany přetahují o prvenství v několika různých rychlostních testech a odpovědí na momentální vítězství strany jedné je obvykle velice rychle nová verze interpretu strany druhé, která situaci opět mění. Z toho samozřejmě v důsledku nejvíc těží uživatel, kterému webové aplikace poběží s každou novou verzí jeho prohlížeče podstatně rychleji.

Ze širšího pohledu je také velice zajímavé, že zrychlování JavaScriptu posouvá „state-of-art“ v oblasti interpretace dynamických jazyků obecně. Dynamické skriptovací jazyky (kam JavaScript patří) totiž obvykle slouží jen jako „lepidlo“ komponent napsaných v jiných, rychlejších jazycích. Jejich rychlost tak není kriticky důležitá a tím pádem se výzkum v oblasti jejich interpretace nedostal příliš daleko – na rozdíl od oblasti kompilace „klasických“ statických jazyků, která je intenzivně zkoumána přes 30 let. Na tom nic nezměnilo ani časté nasazení dynamických jazyků ve webových aplikacích, protože zde je obvykle největší brzdou I/O, resp. databáze. JavaScript je první dynamický jazyk, jehož rychlost je klíčová a zároveň je dostatečně rozšířený na to, aby vznikla dostatečná poptávka po tom ho významně zrychlit.

Důsledkem je, že díky JavaScriptu poněkud ožil výzkum v oblasti interpretace dynamických jazyků, a to jak v týmech zabývajících se vývojem javascriptových interpretů, tak i na univerzitách (např. s technikou tracingu, kterou bude používat interpret JavaScriptu v příští verzi Firefoxu, přišli výzkumníci z University of California). Z tohoto výzkumu můžou samozřejmě těžit i všechny ostatní dynamické jazyky, jako třeba PHP, Perl, Python a nebo Ruby. (Jiná otázka je, jestli skutečně těžit budou.)

Jak je vidět, oblast interpretů JavaScriptu je v současné době pěkně „horká“ a dějí se v ní poměrně zajímavé věci. Právě to je hlavní motivací pro sérii článků, která by tuto oblast zmapovala.

Co nás čeká v příštích dílech?

V příštím díle se podíváme na některé rysy JavaScriptu, které činí největší problémy při jeho implementaci (z pohledu rychlosti). Stručně se také seznámíme se všemi významnými implementacemi JavaScriptu.

V dalších částech seriálu si podrobněji představíme javascriptový interpret zobrazovacího jádra WebKit SquirrelFish, protože ve své původní implementaci je poměrně jednoduchý a budeme si tak na něm moci vysvětlit základní optimalizační techniky. Poté se podíváme na SpiderMonkey používaný ve Firefoxu (včetně jeho vývojové varianty TraceMonkey) a také na nového hráče – V8 od Googlu, který je součástí prohlížeče Google Chrome.

Na úplný závěr seriálu se seznámíme s některými rychlostními testy JavaScriptu – výrobci prohlížečů pomocí nich rádi ukazují, jak se jejich implementace oproti dřívějšku zlepšila. Je docela užitečné vědět, co testy doopravdy testují a umět interpretovat prezentované grafy.

Bude mít zrychlení JavaScriptu vliv i na rychlost dalších dynamických jazyků?

Komentáře

Subscribe
Upozornit na
guest
15 Komentářů
Nejstarší
Nejnovější Most Voted
Inline Feedbacks
View all comments
Brut4r

Nedávno jsem implementoval možnost přesunu řádku v tabulce nahoru, dolu ,úplně nahoru a úplně dolů. Jako nástroj na pomoc jsem zvolil jQuery v poslední verzi (1.2.6) kvůli usnadnění práce s DOM. Výsledkem je cca 100 řádkový script. Blbé je, že na tomto scriptu je vidět rozdíl v rychlost zpracování JS pod Chrome nebo Safari vše běhá nádherně svižně. Pod IE 7 nebo Firefox 3 je rychlost nesrovnatelně pomalejší. Třeba při přesunu řádku v tabulce z horní pozice až dolů přes 70 řádků musí uživatel čekat klidně i 2 sekundy a s narůstajícím počtem řádků v tabulce toto číslo stoupá. Takže doufám, že optimalizace rychlosti se dočkáme i v jiných prohlížečích než jen těch založených na Webkit-u. A idální by bylo kdyby se tyto změny dostali i do starších bverzí těchto prohlížeču.

Brut4r

Zapoměl jsem se přihlásit předchozí příspěvek je ode mě.

m

2 sekundy? V ideálním případě to je 1x removeChild a 1x appendChild (insertBefore), to musí být hned. Chybu bych hledal v tom 100 řádkovým scriptě. :)

Mazarik

Presne tak. Hlavne na taku malu vec nahravat zo serveru jQuery, mi pride strasne. Samozrejme pokial autor pouziva tuto kniznicu aj na inom mieste, tak to ma vyznam.

maros

A co "rendering engine"? Chyba predsa vobec nemusi byt ani v skripte and v JS, ale prave v zobrazeni 70 riadkovej tabulky.

Radek

Nemohl byste při tom srovnávání zmínit i Rhino? Docela by mě zajímalo, jak si stojí a co si o tomto projektu vůbec myslet. Díky!

maros

Toto je dost odvazne tvrdenie: Ze širšího pohledu je také velice zajímavé, že zrychlování JavaScriptu posouvá „state-of-art“ v oblasti interpretace dynamických jazyků obecně. Dynamické skriptovací jazyky (kam JavaScript patří) totiž obvykle slouží jen jako „lepidlo“ komponent napsaných v jiných, rychlejších jazycích. Jejich rychlost tak není kriticky důležitá a tím pádem se výzkum v oblasti jejich interpretace nedostal příliš daleko – na rozdíl od oblasti kompilace „klasických“ statických jazyků, která je intenzivně zkoumána přes 30 let.

Tak toto mi pride trochu pritiahnute za vlasy. Smalltalk je dufam dostatocne dynamicky jazyk a domnievam sa, ze by mohol hravo sutazit s JS zo Safari, WebKitu, Firefoxu a Opery. Staci si spustit lubovolny smalltalk – cele IDE je implementovane samozrejme v smalltalku. Je sice kompilovany do byte-kodu, ale samozrejme, ze nehovorim o nejakom javac'n'java kompilovani a nikto dufam nebrani prehliadacom pouzit JIT.

Odporucam sa pozriet na Just-in-time_compilation#History.
V kazdom pripade by som si netrufol napisat, ze interpretacia dynamickych jazykov sa daleko nedostala, ani ze JavaScript nejak moc k tomu prispel/prispeje. [FLAME]Mozno konecne aj „jazycky“ ako Python a Ruby trochu dotiahnu na Jazyk.[/FLAME]

Pre lenivych: Sun's Self language improved these techniques extensively and was at one point the fastest Smalltalk system in the world; achieving up to half the speed of optimized C[2] but with a fully object-oriented language.

tomas z.

A je Smalltalk taky skriptovací? :)

Taky to moc nechápu. Co to vlastně znamená skriptovací, když v JS skripty asi taky nikdo moc nepíše? A co je to dynamický jazyk? A proč musí být interpretovaný, co brání v tom ho zkompilovat? A neexistují už náhodou kompilované verze? Je kompilovaný Common Lisp dynamický?

tomas z.

"JavaScript je první dynamický jazyk, jehož rychlost je klíčová a zároveň je dostatečně rozšířený na to, aby vznikla dostatečná poptávka po tom ho významně zrychlit." – i v tom odkazovaném blogu je zmínka o C-like speedu u kompilátoru historického dynamického jazyka, takže ta potřeba tu už asi byla dřív, a investovaného úsilí nebylo zas tak málo, a upravován byl i jazyk, ne jen kompilátory. Například dokud v Javascriptu nebudou nepovinné deklarace typu (nebo tam už jsou?), tak jeho kompilátory asi nebudou moci jít tak "na krev" jako ty historických dynamických jazyků.

Aby nedošlo k omylu – to s čím ne zcela souhlasím jsou jen detaily, na seriál se těším, vypadá to zajímavě.

A co je to vlastně ten tracing? V článku je jen zmíněn, v odkázaném blogu o tom taky není… snad příští díl.

Ladislav Thon

> dokud v Javascriptu nebudou nepovinné deklarace typu

Neukázalo se při implementaci Strongtalku, že po všech optimalizacích typu PIC (které se mimochodem používá i ve V8) jsou optimalizace na základě typových informací zbytečné? :-)

Jinak hezký článek o trace trees je třeba tohle FAQ.

Anonymní

Mam rad clanky od autoru, kteri veci rozumi a umi ji vysvetlit poradne a jasne. Tenhle serial se mi zatim jevi, ze bude presne v tomto duchu. Looking forward…

Enum a statická analýza kódu

Mám jednu univerzální radu pro začínající programátorty. V učení sice neexistují rychlé zkratky, ovšem tuhle radu můžete snadno začít používat a zrychlit tak tempo učení. Tou tajemnou ingrediencí je statická analýza kódu. Ukážeme si to na příkladu enum.

Pocta C64

Za prvopočátek své programátorské kariéry vděčím počítači Commodore 64. Tehdy jsem genialitu návrhu nemohl docenit. Dnes dokážu lehce nahlédnout pod pokličku. Chtěl bych se o to s vámi podělit a vzdát mu hold.