Uzávěr (informatika)

V informatice je uzávěr funkce, která má vlastní prostředí. V tomto prostředí je alespoň jedna vázaná proměnná (jméno, které má hodnotu, například číslo). Prostředí uzávěrky uchovává vázané proměnné v paměti mezi jednotlivými použitími uzávěrky.

Peter J. Landin dal této myšlence v roce 1964 název uzávěrka. Programovací jazyk Scheme zpopularizoval uzávěry po roce 1975. Uzávěry má mnoho programovacích jazyků vytvořených po této době.

Anonymní funkce (funkce bez jména) se někdy nesprávně nazývají uzávěry. Většina jazyků, které mají anonymní funkce, má také uzávěry. Anonymní funkce je také uzávěra, pokud má vlastní prostředí s alespoň jednou vázanou proměnnou. Anonymní funkce bez vlastního prostředí není uzávěra. Pojmenovaná uzávěrka není anonymní.

Uzávěry a funkce první třídy

Hodnoty mohou být čísla nebo jiný typ dat, například písmena, nebo datové struktury složené z jednodušších částí. V pravidlech programovacího jazyka jsou hodnotami první třídy hodnoty, které lze zadávat funkcím, vracet funkcemi a vázat na jméno proměnné. Funkce, které přijímají nebo vracejí jiné funkce, se nazývají funkce vyššího řádu. Většina jazyků, které mají funkce jako hodnoty první třídy, má také funkce vyššího řádu a uzávěry.

Podívejte se například na následující funkci Scheme:

; Vraťte seznam všech knih, u kterých se prodalo alespoň TISÍC výtisků. (define (best-selling-books threshold) (filter (lambda (book) (>= (book-sales book) threshold)) book-list)))

V tomto příkladu je lambda výraz (lambda (book) (>= (book-sales book) threshold)) součástí funkce best-selling-books. Při spuštění funkce musí Scheme vytvořit hodnotu lambdy. Udělá to tak, že vytvoří uzávěr s kódem lambdy a odkazem na proměnnou threshold, která je uvnitř lambdy volnou proměnnou. (Volná proměnná je jméno, které není vázáno na hodnotu.)

Funkce filtru pak provede uzávěrku na každé knize v seznamu a vybere, které knihy vrátí. Protože samotný uzávěr má odkaz na hodnotu threshold, může uzávěr tuto hodnotu použít při každém spuštění funkce filter. Samotná funkce filtr může být zapsána ve zcela samostatném souboru.

Zde je stejný příklad přepsaný v ECMAScriptu (JavaScript), dalším populárním jazyce s podporou uzávěrů:

// Vrátí seznam všech knih, u kterých se prodalo alespoň 'threshold' výtisků. function bestSellingBooks(threshold) { return bookList. filter( function(book) { return book. sales >= threshold; }     ); }

ECMAScript zde používá slovo function místo lambda a metodu Array.filter místo funkce filter, ale jinak kód provádí stejnou věc stejným způsobem.

Funkce může vytvořit uzávěr a vrátit jej. Následující příklad je funkce, která vrací funkci.

Ve schématu:

; Vraťte funkci, která aproximuje derivaci f ; pomocí intervalu dx, který by měl být přiměřeně malý. (define (derivative f dx) (lambda (x) (/ (- (f (+ x dx))) (f x)) dx))))

V ECMAScriptu:

// Vraťte funkci, která aproximuje derivaci f // pomocí intervalu dx, který by měl být přiměřeně malý. funkce derivative(f, dx) { return function(x) { return (f(x + dx) - f(x))) / dx; }; }; }

Prostředí uzávěru zachovává vázané proměnné f a dx i po návratu uzavírající funkce (derivace). V jazycích bez uzávěrů by se tyto hodnoty po návratu uzavírající funkce ztratily. V jazycích s uzávěry musí být vázaná proměnná uchovávána v paměti tak dlouho, dokud ji má nějaká uzávěra.

Uzávěr nemusí být vytvořen pomocí anonymní funkce. Například programovací jazyk Python má omezenou podporu anonymních funkcí, ale má uzávěry. Jedním ze způsobů, jak lze výše uvedený příklad ECMAScriptu implementovat v jazyce Python, je například:

# Vraťte funkci, která aproximuje derivaci f # pomocí intervalu dx, který by měl být přiměřeně malý. def derivative(f, dx): def gradient(x): return (f(x + dx) - f(x)) / dx return gradient

V tomto příkladu tvoří funkce s názvem gradient uzávěr spolu s proměnnými f a dx. Vnější obklopující funkce s názvem derivace tuto uzávěrku vrací. V tomto případě by fungovala i anonymní funkce.

def derivative(f, dx): return lambda x: (f(x + dx) - f(x)) / dx

Python musí často používat pojmenované funkce, protože jeho lambda výrazy mohou obsahovat pouze jiné výrazy (kód, který vrací hodnotu), nikoli příkazy (kód, který má účinky, ale nemá hodnotu). V jiných jazycích, například ve Scheme, však veškerý kód vrací hodnotu; ve Scheme je vše výrazem.

Použití uzávěrů

Uzávěry mají mnohostranné využití:

  • Návrháři softwarových knihoven mohou uživatelům umožnit přizpůsobit chování předáváním uzávěrů jako argumentů důležitých funkcí. Například funkce, která třídí hodnoty, může přijmout argument uzávěru, který porovnává hodnoty, jež mají být seřazeny podle kritéria definovaného uživatelem.
  • Protože uzávěry odkládají vyhodnocení, tj. nic "nedělají", dokud nejsou zavolány, lze je použít k definování řídicích struktur. Například všechny standardní řídicí struktury jazyka Smalltalk, včetně větví (if/then/else) a cyklů (while a for), jsou definovány pomocí objektů, jejichž metody akceptují uzávěry. Uživatelé mohou snadno definovat i vlastní řídicí struktury.
  • Lze vytvořit více funkcí, které se uzavírají nad stejným prostředím, což jim umožňuje soukromou komunikaci změnou tohoto prostředí (v jazycích, které umožňují přiřazení).

Ve schématu

(define foo #f) (define bar #f) (let ((secret-message "none")) (set! foo (lambda (msg) (set! secret-message msg))) (set! bar (lambda () secret-message))) (display (bar)) ; vytiskne "none" (newline) (foo "meet me by the docks at the midnight") (display (bar)) ; vytiskne "meet me by the docks at the midnight".
  • Uzávěry lze použít k implementaci objektových systémů.

Poznámka: Někteří mluvčí nazývají uzávěrem jakoukoli datovou strukturu, která váže lexikální prostředí, ale tento termín se obvykle vztahuje konkrétně na funkce.

Otázky a odpovědi

Otázka: Co je to uzávěrka v informatice?


Odpověď: Uzávěr je funkce, která má své vlastní prostředí.

Otázka: Co obsahuje prostředí uzávěru?


Odpověď: Prostředí uzávěru obsahuje alespoň jednu vázanou proměnnou.

Otázka: Kdo dal myšlence uzávěru jméno?


Odpověď: Myšlenku uzávěru pojmenoval Peter J. Landin v roce 1964.

Otázka: Který programovací jazyk zpopularizoval uzávěry po roce 1975?


Odpověď: Uzávěry zpopularizoval po roce 1975 programovací jazyk Scheme.

Otázka: Jsou anonymní funkce a uzávěry totéž?


Odpověď: Anonymní funkce se někdy nesprávně nazývají uzávěry, ale ne všechny anonymní funkce jsou uzávěry.

Otázka: Co dělá z anonymní funkce uzávěr?


Odpověď: Anonymní funkce je uzávěra, pokud má vlastní prostředí s alespoň jednou vázanou proměnnou.

Otázka: Je pojmenovaná uzávěrka anonymní?


Odpověď: Ne, pojmenovaná uzávěra není anonymní.

AlegsaOnline.com - 2020 / 2023 - License CC3