sobota 17. srpna 2019

Programovací a skriptovací jazyky

Počítačových jazyků dnes existuje nepřeberné množství, proto bývá užitečné je seskupovat do různých kategorií podle míry abstrakce, využití, způsobu běhu apod. Jedním z nich je i rozdělení jazyků na programovací a skriptovací (pojem "programovací jazyky" může být brán obecně jako všechny jazyky i konkrétně jako opak skriptovacích).

Jak už to tak bývá, i toto rozdělení je vcelku vágní. Už jsem viděl situace, kdy byl třeba jazyk C (drtivě programovací) použit pro psaní skriptů nebo kdy v JavaScriptu (převážně skriptovacím jazyce) byly napsány velké programy. Obecně se dá říct, že jazyky programovací jsou určené pro psaní programů, zatímco skriptovací jsou určené pro psaní skriptů, ale některé lze použít i pro druhý účel.

Jenomže jsme si tím moc nepomohli, neboť už ani samotné pojmy program a skript nejsou dobře definované. Program bývá tradičně izolovaný kus kódu, který může běžet samostatně, zatímco skript běží v rámci nějakého prostředí. Problém ale nastane, když si uvědomíme, že i programy vlastně běží pod operačním systémem, se kterým musejí komunikovat (pomocí API), takže i v jejich případě existuje nějaké prostředí. Můžeme z možných prostředí odstranit operační systém, ale co virtuální běhové prostředí .NET a JRE pro C# a Javu? Je kód v Lue, PHP či Haskellu, spuštěný v korespondujícím interpretru, stále program, či už skript? A co kus JavaScriptu spuštěný prohlížečem na webové stránce?

Napadlo mě, že bych tyto pojmy definoval přesněji, což by možná pomohlo při klasifikaci některých jazyků. Podle mé nové definice je program kód, jehož části mohou být vykonávány jen současně s jeho tělem. Tělo je pak hlavní procedura celého programu, s jejímž začátkem program vzniká a s jejímž koncem program zaniká. Když skončí tělo programu, už z něj nic nezbyde.

Oproti tomu skript po sobě často něco zanechává. Obsluha webové stránky v JavaScriptu či herní kód v Lue často reaguje na určité podněty generované prostředím, jejichž kód bývá vyvolán i poté, kdy skončí tělo skriptu.

Kupříkladu aplikace, která při spuštění vytvoří okno kalkulačky, reaguje na stisknutí tlačítek a počítá výsledky operací, je program, pokud součástí kódu je nějaká hlavní procedura, na jejímž začátku okno ještě neexistuje a na jejímž konci je už okno definitivně zavřené. Pokud hlavní procedura chybí (uživatelský kód jej neinicializuje), musí logicky existovat nějaké řídící prostředí, které se postará o jeho vytvoření. To zní trochu ezotericky, ale webová kalkulačka je perfektní příklad takového případu: webový prohlížeč (zde program) vytvoří reprezentaci stránky (pomocí deklarativního HTML) a poté spouští různé kusy kódu v JavaScriptu v závislosti na tom, co uživatel na stránce udělal. Pokud by existovalo nějaké newebové prostředí, které by fungovalo stejně (např. WPF neumožňující metodu Main), nebyl by v tom žádný rozdíl.

Pokud bych do své kalkulačky přidal podporu pluginů/zásuvných modulů, které bych informoval o všem, co se v kalkulačce děje (pomocí událostí), stává se moje aplikace prostředím pro skripty, ať jsou psané v C++ nebo Lue. Pokud by ale nějaký plugin převzal řízení nad aplikací (např. vytvořil modální okno), kde by kupříkladu kreslil grafy, stane se z něj program. Řízení klidně může předávat aplikaci zpět (koneckonců to samé dělá multitasking v OS), ale jeho průběh musí být jasně určen tělem.

Toto rozlišení nám umožní definovat jazyky ryze programovací (musí obsahovat tělo, které podmiňuje běh kódu programu) a ryze skriptovací (nemohou obsahovat tělo; vše je řízeno obsluhou událostí). Pokud bych vynutil v jazyce C funkci main, bude to jazyk ryze programovací, neboť vše v něm definované musí na jejím konci zaniknout. Naopak pokud bych v Lue zabránil vykonávat příkazy mimo funkci (např. tím, že globální prostředí poskytnu až po skončení těla skriptu) kromě inicializace se nebude moci takový skript nijak navenek projevovat, a tedy takový jazyk bude ryze skriptovací.

Jak je patrné z příkladů, reálné jazyky zapadají někam mezi tyto dvě kategorie. I programovací jazyk C++ mohu použít jako skriptovací v jiném programu tak, že spustím kompilátor, za běhu dynamicky načtu výsledek a zavolám v něm exportované funkce, a stejně tak interpretr JavaScriptu můžu spustit na kódu tak, že zanikne, jakmile skončí jeho tělo.

Skutečnost se má tak, že mnohdy to, zdali je nějaký jazyk programovací či skriptovací, závisí na konfiguraci prostředí. Operační systém či interpretr Luy jsou programy určené ke spouštění jiných programů a tak s nimi zacházejí, zatímco webový prohlížeč či hra je prostředí určené ke spouštění skriptů.

Příklad jazyka, který by se dal označit za hybridní, je Pawn. Ačkoliv je staticky typovaný, kompilovaný a má funkci main (tedy obsahuje rysy programovacích jazyků), je primárně určen pro psaní vnořeného kódu pro existující systémy, tedy pro psaní skriptů. Vstupní body v Pawnu jsou všechny veřejné (exportované) funkce a funkce main, přičemž má-li kód pouze veřejné funkce (a nikoliv main), jeho běh je zcela řízen prostředím a tudíž se jedná o skript, zatímco pokud kód má pouze funkci main, má jen jediný možný průběh a jedinou možnost, jak se projevit, a tudíž se jedná o program.

Tato definice není nikterak absolutní a jako podobné definice těchto termínů nemusí být ani tak užitečná, ale podle mého názoru je rozhodně zajímavé přemýšlet o návrzích jazyků z různých úhlů pohledu, zvláště když to určuje, na co se jazyky dají použít a na co nikoliv.

Na závěr je ještě nutno dodat, kam patří jazyky jako HTML či XML. Nikam, protože to nejsou aktivní jazyky, tedy jazyky umožňující zápis kódu, který něco vykonává. Pokud by programy byly na jedné straně škály a skripty na druhé, kód v HTML by přečníval dál za skripty, protože v takovém případě má prostředí absolutní moc nad tím, jak jej interpretovat.
 
Dodatek: Mluvit o webových stránkách v rámci tohoto srovnání je možná trochu nešikovné, protože každá stránka se skládá z mnoha komponent, kde ty aktivní nemají zdaleka tak velkou váhu, jako tomu bývá u klasických programů. Kód v HTML, CSS i JS existuje v rámci jednoho celkového programu, který vzniká otevřením stránky a zaniká jejím zavřením, ale ačkoliv zde prohlížeč figuruje podobně jako OS spuštěním tohoto programu, zároveň ho i (narozdíl od OS) také vytváří z poskytnutých součástí.

Druhý dodatek: Mimo toto rozdělení stojí i některé kódy, které se též tradičně nazývají programy, například lineární programy. Ty stojí na stejném místě jako XML, protože pouze popisují proměnné a jejich vztahy a slouží jen k vybudování nějakého objektu.

Žádné komentáře:

Okomentovat