Vyhodnocovacia stratégia

**Vyhodnocovacia stratégia** (tiež redukčná stratégia – pojem sa typicky používa vo funkcionálnych jazykoch) v programovacom jazyku je množina pravidiel (väčšinou deterministických), ktorá definuje spôsob vyhodnocovania výrazov. Typicky je dôraz kladený na funkcie a operátory – vyhodnocovacia stratégia definuje kedy a v akom poradí sú vyhodnocované argumenty funkcie, kedy a akým spôsobom sú vo funkcii nahradzované.

Jazyk môže kombinovať niekoľko vyhodnocovacích stratégií. Napríklad C++ kombinuje volanie hodnotou a volanie referenciou. Väčšina jazykov, ktoré sú prevažne striktné, používajú nejakú formu nestriktného vyhodnocovania pre booleovské výrazy a podmienené príkazy.

## Striktné vyhodnocovanie
V *striktnom vyhodnocovaní* sú argumenty funkcie vždy úplne vyhodnotené pred tým ako sú na funkciu aplikované (aplikácia argumentov na funkciu je v imperatívnych jazykoch často označovaná ako volanie funkcie s danými argumentmi).

### Volanie hodnotou
*Volanie hodnotou* je najčastejšia vyhodnocovacia stratégia, používaná napríklad v jazyku C. Pri volaní hodnotou je argument výrazu vyhodnotený a výsledná hodnota je priradená k zodpovedajúcej premennej vo funkcii (obvykle skopírovaním hodnoty na nové miesto v pamäti). Ak je dovolené, aby funkcia, alebo procedúra mohla priradiť hodnoty svojim argumentom, táto hodnota je priradená iba lokálnej kópii. To znamená, že čokoľvek volajúci pomocou argumentov odovzdal funkcii má po vrátení z volania funkcie volajúci v svojom rozsahu platnosti nezmenené.

### Volanie referenciou (odkazom)
*Volanie referenciou* je spôsob vyhodnocovania používaných v niektorých jazykoch (napríklad C++), kde premenné a niektoré iné hodnoty, nazývané *l-hodnotou* (anglicky l-value), musia vždy odkazovať na nejaké miesto v pamäti. V týchto jazykoch niektoré funkcie ako svoje argumenty akceptujú iba l-hodnoty. S l-hodnotou sa musí vždy zaobchádzať ako s referenciou a musí byť predaná funkcii *pomocou hodnoty*. Telo funkcie môže potom manipulovať s obsahom referencovanej bunky pamäte, zmenou hodnoty na ktorú l-hodnota ukazuje vo rozsahu platnosti volajúceho.

V jazykoch, ktoré používajú neobmedzované ukazovatele namiesto alebo spolu s referenciami, je *volanie adresou* variantov k volaniu referenciou, kde referencia je neobmedzený ukazovateľ.

Niektoré jazyky používajú referencie, alebo ukazovatele ako špeciálne hodnoty. Napríklad ML má „ref“ konštruktor, jazyk C intenzívne využíva ukazovatele. V týchto jazykoch je „volanie referenciou“ alebo „volanie adresou“ môže byť použité ako spôsob odovzdania hodnoty referencie, alebo hodnoty ukazovateľa ako argumentu funkcie.

## Nestriktné vyhodnocovanie
V *nestriktnom vyhodnocovaní* nie sú argumenty funkcie vyhodnocované, kým nie sú práve použité pri vyhodnocovaní tela funkcie.

### Normálne vyhodnocovanie
*Normálne vyhodnocovanie* je vyhodnocovacia stratégia, kde je pri aplikovaní funkcie redukovaná tá funkcia, ktorá je najviac vonku, bez toho aby boli vyhodnotené funkčné argumenty. Od *volania menom* sa líši tým, že sa nevyhodnocuje vnútorné telo neaplikovanej funkcie.

### Volanie menom
Vyhodnocovanie *volanie menom* je zriedka implementované priamo, ale často je použité pri uvažovaní nad teoretickými vlastnosťami programov a programovacích jazykov. Pri vyhodnocovaní *volaním menom* nie sú argumenty funkcie vôbec vyhodnocované – skôr sú argumenty funkcie priamo nahradené vo funkčnom tele. Keď argument nie je vôbec použitý, tak sa nikdy nevyhodnotí. Keď je argument používaný niekoľkokrát, tak je vždy znovu vyhodnocovaný. Z tohto dôvodu sa sémantika volania menom zvyčajne implementuje *volaním podľa potreby*.

### Volanie podľa potreby
*Volanie podľa potreby* je memoizovaná vyhodnocovacia verzia *volania menom*. Keď je prvýkrát vyhodnotený argument funkcie, tak sa jeho hodnota uloží (odtiaľ to memoizovanie). Pri ďalšom vyhodnocovaní sa použije uložená hodnota. Keď je argument používaný dva alebo viackrát, tak je volanie podľa potreby takmer vždy rýchlejšie ako volanie menom. V jazyku, ktorý má „čisté“ výrazy (bez vedľajších efektov), toto dáva rovnaké výsledky ako pri volaní menom. 

*Volanie podľa potreby* sa dá použiť iba v jazykoch, ktoré zaručujú referenčnú transparentnosť – napríklad pri deklaratívnych, alebo funkcionálnych jazykoch. Pri imperatívnych jazykoch toto nie je zaručené na 100% (pretože vyhodnocovanie výrazu závisí na stave, v ktorom sa program nachádza – vo výraze sa môže meniť hodnota globálnej premennej a pri každom vyhodnotení môže mať tento výraz inú hodnotu).

Kategória:Informatika