Syntaxe a sémantika programovacího jazyka Wolfram Language

Z Wikipedie, otevřené encyklopedie
Související informace naleznete také v článcích Wolfram Language, Mathematica a Srovnání Pythonu a Wolfram Language.

Syntaxe a sémantika programovacího jazyka Wolfram Language představuje sadu pravidel, podle nichž lze psát kód v programovacím jazyce Wolfram Language (dále jen WL), spolu s tím, jak je tento kód interpretován. Tato stránka přináší podrobnější přehled základní funkcionality, než jak je podán v článku Wolfram Language. Pokud není vysloveně uvedeno jinak, je v následujícím použita verze WL 13.0.0.

Syntaxe WL v mnohém připomíná syntaxi jiných programovacích jazyků jako C či Java. WL je case sensitive, přičemž názvy funkcí a přednastavených konstant se řídí konvencí CamelCase. Počáteční písmeno je tedy velké a pokud se název skládá z několika slov, tak je velké i počáteční písmeno každého slova[1], viz např. ListPlot, StringJoin či FunctionCompile. Pojmenovávání předdefinovaných funkcí a proměnných je ve WL poněkud rozvláčné, srovnej např. funkce SingularValueDecomposition a StandardDeviation, jejichž varianty v MATLABu zní svd a std. Navíc je obecně snaha vývojářů WL nečlenit funkce do balíčků, které by bylo potřeba před použitím importovat, ale téměř všechny funkce jazyka jsou k dispozici přímo v hlavním jmenném prostoru.

Každá funkce či konstrukt má ve WL jméno, jež často odpovídá jemu anglickému názvu. Některé z nich lze pak reprezentovat speciálními znaky, známými z jiných jazyků. Například sčítání se provádí znakem +, násobení znakem *, skládání řetězců znakem <>, apod. Této reprezentaci se říká InputForm. Tyto operace lze nicméně vyjádřit i pomocí písmen anglické abecedy. Například výraz a + b lze zapsat též jako Plus[a, b], výraz a * b jako Times[a, b], výraz "retezec 1"<>"retezec 2" jako StringJoin["retezec 1", "retezec 2"] atd. Tato reprezentace se jmenuje FullForm[2]. V následujícím bude často k dané funkci či operátoru zmíněna nejen obvyklá syntaxe, ale právě i její FullForm.

Základy[editovat | editovat zdroj]

Identifikátory[editovat | editovat zdroj]

Vývojář WL nenabízí veřejnou specifikaci toho, co může a co nemůže být identifikátor. Obecně ale nemůže být prvním znakem názvu číslice a podporována je pro znaky celá sada Unicode[3] včetně znaků české abecedy. Interní konstanty a proměnné začínají konvenčně znakem dolaru $, viz např. $Output či $FontFamilies.

Na rozdíl od některých populárních jazyků nelze použít podtržítko jako součást jména proměnných či funkcí, protože je mu vyhrazena funkce ve vzorech. Pro mnoho znaků existuje ve WL jméno, které se vkládá do konstruktu \[...], např. lze získat zapsáním \[RightArrow]. Pro mnoho znaků, jako třeba písmena alfabety, též existuje alias, to jest zkratka, kterou lze zapsat mezi dvěma stisknutími klávesy ESC, aby se vytvořil odpovídající znak. Znaky lze vkládat i pomocí jejich jmen v jazyce HTML či systému TeX způsobem podobný aliasům, a tak např. ESC &aacute ESC vrátí á, ESC \infty ESC vrátí apod.[4] Konečně, libovolný znak Unicode lze vložit vypsáním \:nnnn či \|nnnnnn, kde nnnn či nnnnnn je hexadecimální kódový bod daného znaku[5].

Komentáře[editovat | editovat zdroj]

Na rozdíl od některých jazyků jako např. C++ či Java existuje ve WL jen jeden druh komentářů, kde je text komentáře uzavřen mezi kulaté závorky s hvězdičkami[6]:

a = 1; (* toto je komentář *)
(* komentář může přesahovat
několik řádek *)
b = a + 2;

Předešlé výstupy[editovat | editovat zdroj]

Jádro WL udržuje přehled o výsledcích všech předešlých příkazů odeslaných uživatelem z front endu[pozn. 1]. Vyvolat hodnotu posledního příkazu lze symbolem procenta[7]. Tak například volání

1+2;
%

vrátí hodnotu 3. Chceme-li vyvolat předposlední výsledek, napíšeme znak procent dvakrát (%%); pro výsledek třetí od konce napíšeme tento znak třikrát atd. Každému výstupu je navíc přiřazeno číslo, které je pro daný běh jádra jedinečné a tak pokud víme číslo daného výstupu, řekněme 51, lze odpovídající výstup vyvolat napsáním %51.

Nápověda[editovat | editovat zdroj]

Krátkou nápovědu k danému symbolu lze programově zobrazit v editoru napsáním otazníku na začátku řádku[6], následovaným jménem symbolu. Krátký popis funkce sinus tak lze obdržet voláním:

?Sin

Pokud místo jednoho otazníku použijeme otazníky dva, obržíme detailnější nápovědu (??Sin)[8][pozn. 2]. Programové volání nápovědy lze rozšířit o žolíkové znaky, kde * označuje libovolný počet libovolných znaků a @ označuje libovolné malé písmeno. Tak například volání ?P*i vrátí ve verzi 13.1.0 dva nálezy a sice Pi a PrimePi. Hledání lze tímto způsobem dále rozšířit na celé jmenné prostory. K vypsání všech symbolů definovaných ve jmenném prostoru (kontextu) Global stačí napsat[9]:

?Global`*

Datové typy[editovat | editovat zdroj]

Jedním za základních designových principů WL je ten, že „vše je výraz“[10]. Výraz, anglicky expression, je buď atomární, viz níže, anebo normální, a pak má obecný tvar

hlava[arg1, arg2, ...]

kde hlava je hlavička výrazu, jíž lze dostat voláním funkce Head, a kde za hlavičkou následuje v hranatých závorkách nula či více výrazů oddělených čárkami. Tento obecný tvar sledují konstrukty typu If či For, volání funkcí, specifikace stylu apod. Hlavička samotná může být buď symbol, např. název funkce, anebo další výraz. Takovým případem může být např. výraz (#&)[x], který má za hlavičku ryzí funkci #&, jež je samotná specifikována interně výrazem Function[Slot[1]].

Dokonce i zápis tvaru něco; něco2; něco3 je vyhodnocen jako výraz a sice výraz tvaru CompoundExpression[něco, něco2, něco3][11]. Výrazy lze do sebe vnořovat a vytvářet tak strukturovaná data a kód. Podvýraz na jisté úrovni vnoření lze získat pomocí funkce Level. Rozvětvení pomyslného stromu vnořených výrazů lze kvantifikovat pomocí funkce LeafCount. Jisté konstrukty, jako čísla či řetězce, jsou považovány za atomární[pozn. 3] a stojí na posledním stupínku vnoření. Tyto jsou představeny v sekcích níže. Viz též následující oddíl „Datové struktury“.

Symboly[editovat | editovat zdroj]

Jedním ze základních typů ve WL jsou symboly, to jest výrazy s hlavičkou Symbol[12]. Funkce (kromě těch ryzích), předdefinované konstanty atd. jsou symboly. Na rozdíl od jiných jazyků jako C či Python[13] nejen že nemusí být proměnná inicializována, ale nemusí mít ani přiřazenu žádnou hodnotu, a tak například následující vstupní kód je bez problémů ve WL interpretován

x

Dokud není do proměnné uložena konkrétní hodnota, tak se tato chová jako symbolická proměnná, kterou lze využít pro symbolické výpočty[pozn. 4], a tak např.

y = x + 2;
y^2 (* vrátí: (2 + x)^2 *)
Expand[y^2] (* vrátí: 4 + 4 x + x^2 *)

kde funkce Expand rozepisuje mocniny výrazů do jednotlivých členů.

Chceme-li vymazat hodnotu proměnné var, lze toto učinit buď zápisem x = ., či voláním Clear[x][14][pozn. 5]. Tento přístup pouze smaže hodnotu proměnné, ponechá nicméně její jméno k dispozici výpočetnímu jádru. Pokud chceme proměnnou vyjmout úplně, lze toto provést funkcí Remove. Název symbolu nemůže mj. začínat číslicí, nesmí obsahovat podtržítka, může ale např. obsahovat znaky české abecedy.

Čísla[editovat | editovat zdroj]

WL má několik číselných datových typů, Integer odpovídá celým číslům, Rational racionálním číslům, Real číslům reálným a Complex číslům komplexním[15]. Poslední dva typy jsou typy s pohyblivou řádovou čárkou. Jakmile jsou vstupní hodnoty funkcí typu Integer či Rational, snaží se WL spočíst výsledek naprosto přesně, to jest s nekonečnou přesností. To ale může vést k neúměrně dlouhému výpočtu. Srovnej následující kód:

x = 3; (* 3 je typu Integer *)
x^2 + Sqrt[x] (* vrátí 9 + Sqrt[3] *)
y = 3.; (* 3. je typu Real *)
y^2 + Sqrt[y] (* vrátí 10.7321 *)

Vědecký zápis čísel pomocí mantisy a exponentu, který má v mnoha jazycích syntaxi ve stylu 12.34e3 se ve WL provede způsobem 12.34*^3. Pokud je počáteční číslice desetinného čísla rovna nule, lze tuto vynechat a tedy .1 je totéž co 0.1. Čísla lze zadávat i v jiné než desítkové soustavě (podporovány jsou soustavy o základu 2 až 36) a to tak, že se před číslo uvede základ soustavy následovaný dvěma stříškami[16]: 2^^101 je binární zápis čísla 5, 16^^ff je šestnáctkový zápis čísla 255 apod.

Přesné výrazy lze převést na floating-point výrazy voláním funkce N, kde lze jako druhý nepovinný parametr uvést přesnost výsledného výrazu. WL rozlišuje absolutní přesnost čísel (Accuracy) a relativní přesnost (Precision)[17]. Při zápisu čísla lze Accuracy udat jako číslo za dvěma zpětnými apostrofy ``, Precision pak jako číslo za apostrofem jedním `:

3.14``20 (* Accuracy je 20 *)
3.14`20 (* Precision je 20 *)
3.14 (* Accuracy a Precision mají výchozí hodnoty dané strojem, na kterém WL běží *)
3 (* Accuracy i Precision jsou nekonečné *)
N[(1 + Sqrt[2])/5] (* vrátí: 0.482843 *)

Číslům s pohyblivou řádovou čárkou lze nastavit libovolně velkou přesnost[18]. Pokud tato nicméně překročí přesnost stroje, na kterém WL běží, je vyšší přesnosti interně docíleno softwarovými prostředky, což může velmi zpomalovat výpočetní jádro. Všechny dosud uvedené notace lze kombinovat a tak například zápis 2^^10011.1011`8*^3 označuje číslo 158.0.

Ve WL je předdefinováno množství konstant jako nekonečno (Infinity), jež lze dostat například dělením nenulového čísla nulou, nerozhodnutelné (Indeterminate), jež lze dostat dělením nuly nulou, $MachineEpsilon, jež označuje nejmenší rozlišitelné číslo, $MaxMachineNumber, jež označuje největší reprezentovatelné floating-point číslo atd.[19][20] Podporováno je i mnoho matematických konstant jako číslo (Pi), eulerovo číslo (E), zlatý řez (GoldenRatio), atd.[21]

Řetězce[editovat | editovat zdroj]

Textové řetězce jsou uvozeny dvojitými uvozovkami, jednoduché uvozovky použít nelze. Podobně jako pro názvy proměnných a funkcí, i v řetězcích lze použít libovolné Unicode znaky včetně písmen české abecedy. Jsou podporovány některé typické escape sekvence jako uvozovky \", odřádkování \n či tabulátor \t[22]. Podporována je řada operací na řetězcích[23]. Například zřetězení dvou (a více) textových řetězců r1 a r2 lze provést voláním r1<>r2 či ekvivalentně StringJoin[r1, r2]. Získání znaku na daném místě řetězce lze provést funkcí StringPart. A tak například:

"Příklad řetězce"
"Začátek"<>"Konec" (* vrátí: "ZačátekKonec" *)
"První řádek\nDruhý řádek" (* vypíše odřádkovaný řetězec *)
StringPart["abcd", 2] (* vrátí: "b" *)

Obecný výraz lze přeměnit na řetězec voláním funkce ToString[pozn. 6]. Opačně, je-li v řetězci uložen platný kód, lze tento řetězec na kód převést funkcí ToExpression[24]. Řetězce lze vypisovat pomocí funkce Print, která přijímá i neřetězcové výrazy, na něž tedy není třeba volat zvlášť ToString, přičemž tyto výrazy jsou vykresleny ve své původní formě. Chceme-li do řetězce dosadit parametry, lze buď použít funkci StringForm nebo novější funkci StringTemplate[25], která nabízí širší možnosti za cenu složitějšího zápisu. Lze pak psát například:

ToString[StringForm["Součtem `1` a `2` obržíme `3`.", 2, 3, 5]] (* vrátí: "Součtem 2 a 3 obržíme 5." *)
StringTemplate["Součtem `1` a `2` obržíme `3`."][2, 3, 5] (* vrátí: "Součtem 2 a 3 obržíme 5." *)

Na rozdíl od jiných jazyků jsou podporovány i složitější konstrukty uvnitř řetězců, které umožňují pokročilejší formátování výstupu. Například zlomek „a / b“, kde je čitatel přímo nad jmenovatelem tak, jak je běžné v matematické notaci, lze zapsat do řetězce jako "\!\(\*FractionBox[\(a\), \(b\)]\)"[26][5]. Uživatel s touto nízkoúrovňovou reprezentací nicméně nepracuje, protože v editoru se zobrazí pouze samotný zlomek. Dále WL podporuje řetězcové vzory (angl. string patterns)[27], což jsou obdoby regulárních výrazů z jiných jazyků, viz oddíl „Regulární výrazy“.

Datové struktury[editovat | editovat zdroj]

Základní datovou strukturou ve WL je pole představované konstruktem List, k níž se od verze 10.0 přidalo asociativní pole (hashovací tabulka) představované konstruktem Association. Oba jsou podrobně představeny níže. WL podporuje ale i další druhy datových struktur jako řídká pole (SparseArray), pole s dodatečnými symetriemi (SymmetrizedArray), pole s fyzikálními jednotkami (QuantityArray), či řadu tradičních struktur[28], jež lze obdržet jako speciální případ konstruktu DataStructure. Na rozdíl od některých jiných jazyků nemá WL datový typ odpovídající množinám, kam by šel daný prvek vložit pouze jednou.

List[editovat | editovat zdroj]

Pole je datová struktura, jejíž prvky mohou být různých typů — od čísel, přes řetězce, po obrázky či zvukové záznamy. Prvkem může být i další pole, čímž lze vytvářet vícerozměrná pole[29]. Pole se zapisují pomocí složených závorek {prvek1, prvek2, prvek3, ..., prvekN}, kde jsou jednotlivé prvky odděleny čárkou[30]. Pole je ve WL představováno výrazem s hlavičkou List, znamenající anglicky seznam. Dvojrozměrné pole celých čísel může vypadat třeba takto:

p = {{5, 1, 3}, {7, 0}, {2, 1, 6, 8}, {-3, 1, 1}}

Zdůrazněme, že počet prvků nemusí být v každém vnořeném poli stejný. Počet prvků lze zjistit příkazem Length. Je-li počet prvků v každém vnořeném poli shodný, lze tento počet pro každou dimenzi zjistit příkazem Dimensions.

Indexování pole se provádí zapsáním dvojitých hranatých závorek, do kterých se uvede index, přičemž indexování probíhá od jedničky[31]. Pro získání druhého vnořeného pole v poli p definovaném výše tak lze zapsat p[[2]]. Indexovat lze i od konce pomocí záporných čísel. Poslední prvek tak lze obdržet voláním p[[-1]], předposlední p[[-2]] atd. Chceme-li namísto jediného prvku získat rozsah prvků od indexu i1 po index i2, stačí zapsat p[[i1;;i2]], kde jsou mezi indexy vloženy dva středníky. Konstrukt p[[i1;;i2;;k]] vrátí pak každý k-tý prvek v daném rozsahu. Pokud namísto rozsahu chceme dostat jen několik vybraných prvků, lze tyto obdržet jediným voláním tvaru p[[{i1, i2, ..., ik}]], kde jsou indexy jednotlivých prvků ohraničeny složenými závorkami. V případě dvourozměrných polí lze indexovat dvěma způsoby — buď stylem p[[i1]][[i2]], nebo kompaktněji p[[i1, i2]]. Oba způsoby lze použít i pro vícerozměrná pole. Změnit hodnotu daného prvku pak lze přiřazením ve tvaru:

p[[3, 2]] = 42;

Takovéto přiřazení upravuje seznam in place[32].

Interně je pole reprezentováno dvěma různými způsoby v závislosti na typu dat, která obsahuje. V obecném případě obsahuje pole pouze adresy na jednotlivé části paměti, ve kterých jsou uloženy prvky samotné. Pokud je ale typ všech prvků (v jedno- i vícerozměrných polích) stejný a číselný a současně je počet prvků v každé dimenzi shodný, může WL pro zvýšení výkonu použít efektivnější reprezentaci označovanou jako PackedArray[33][34][pozn. 7], která je více podobná způsobu, jakým je pole reprezentováno např. v jazyce C jako souvislý blok paměti.

Pole podporují operace jako řazení (Sort), vektorové operace jako vektorový součin (Cross) či množinové operace jako sjednocení (Union). Dvourozměrná pole lze interpretovat jako matice — v takových případech lze použít maticové operace jako maticový součin (Dot[A, B] pro matice A a B, popř. totéž zkráceně pomocí tečky A.B), determinant (Det), apod.[35]

Association[editovat | editovat zdroj]

Asociativní pole jsou imutabilní datové struktury[36][37] zavedené ve verzi 10.0 a jsou představována výrazem Association[k1->h1, k2->h2, ..., kN->hN] či ekvivalentně zápisem <|k1->h1, k2->h2, ..., kN->hN|>, kde k1 atd. jsou klíče a h1 atd. jsou jim odpovídající hodnoty. Za klíč může přitom sloužit libovolný výraz[38]. Seznam klíčů lze obdržet voláním funkce Keys, jim odpovídající hodnoty pak funkcí Values.

Pokud chceme dostat hodnotu pro klíč k v asociativním poli a, píšeme a[k] s jednoduchými hranatými závorkami[39]. Na rozdíl od jiných jazyků si v WL asociativní pole uchovává i informaci o pořadí svých prvků a tak na něj lze použít i indexování známé ze seznamů. Máme-li asociativní pole tvaru a = <|"r"->3, "s"->5, "t"->7, "u"->9|>, lze hodnotu 7 obdržet buď voláním a["t"] či indexováním a[[3]], protože je pár ("t", 7) třetím prvkem v asociativním poli a. Oba způsoby lze zkombinovat tak, že se pro indexování použije místo indexu samotný klíč, obalený do výrazu Key, a sice a[[Key["t"]]][40]. Tento hybridní zápis je užitečný ve chvíli, kdy je asociativní pole prvkem nějakého seznamu a/nebo je hodnota pro daný klíč seznamem obsahující další prvky. Máme-li tedy například seznam tvaru:

s = {3, 2, <|5->{8, "retez"}, "x"->42, y->Sin|>, "a"}

lze hodnoty "retez" a 42 obdržet voláním

s[[3, Key[5], 2]] (* vrátí "retez" *)
s[[3, "x"]] (* vrátí 42 *)

V posledním řádku je využit fakt, že pokud je klíčem řetězec, lze hlavičku Key vynechat. Asociativní pole nepodporují jen Rule, ale i odložené RuleDelayed, kterýžto rozdíl se projeví například při použití funkcí jako RandomReal:[pozn. 8]

a = <|k:>RandomReal[]|>;
a[k] (* vrátí 0.778739  *)
a[k] (* vrátí 0.003326  *)

Asociativní pole lze kromě manuálního vypsání vytvořit různými způsoby[39]. Máme-li například seznam výrazů {e1, ..., eN}, pro něž chceme spočíst nějakou vlastnost a výsledná data pak uložit do asociativního pole, lze použít funkci AssociationMap, která vezme jistou funkci f a tu aplikuje zvlášť na každý výraz. Výsledkem je pak asociativní pole tvaru <|e1->f[e1], ..., eN->f[eN]|>, kde klíče jsou původními výrazy a jim odpovídající hodnoty jsou návratové hodnoty funkce f. Podobně, máme-li seznam klíčů {k1, ..., kN} a zvlášť seznam hodnot {h1, ..., hN}, lze tyto přetvořit do asociativního pole voláním ve tvaru AssociationThread[{k1, ..., kN} -> {h1, ..., hN}], jež vrátí výraz <|k1->h1, ..., kN->hN|>.

Obyčejně jsou funkce aplikovány na hodnoty asociativního pole, klíče jsou přeskakovány. Pokud chceme aplikovat danou funkci jen na klíče, lze toto učinit pomocí funkce KeyMap. Chceme-li manipulovat s celým párem (klíč, hodnota), lze použít funkci KeyValueMap. V ryzích funkcích lze navíc místo pozičního slotu použít slot pojmenovaný po daném klíči[41]. Uvažme například seznam asociativních polí {a1, a2, ..., aN}, z nichž každé obsahuje klíč "klic", kde naším úkolem je získat seznam hodnot odpovídajících tomuto klíči. Toto lze učinit kódem #klic & /@ {a1, a2, ..., aN}, kde #klic je slot ryzí funkce.

Asociativní pole <|k1->h1, k2->h2, ..., kN->hN|> může svým zápisem velmi připomínat seznam {k1->h1, k2->h2, ..., kN->hN}, jehož prvky jsou výrazy Rule tvaru klič->hodnota. Takovýto seznam nicméně nepodporuje vyhledání hodnoty pomocí jejího klíče. Chování asociativního pole lze do jisté míry emulovat použitím indexovaných proměnných (angl. indexed variable)[42], což jsou proměnné, pro něž jsou definovány výrazu tvaru proměnná[klíč] = hodnota; např.:

a[1] = foo;
a["asdf"] = bar;

V tomto případě nemá symbol a přiřazenu žádnou hodnotu. Hodnotu mají přiřazenu jen výrazy a[1] a a["asdf"].

Operátory[editovat | editovat zdroj]

Aritmetika[editovat | editovat zdroj]

WL podporuje tradiční aritmetické operace s čísly[43] jako sčítání (a + b), odčítání (a - b), násobení (a * b), dělení (a / b), spolu s unárními operaci ve stylu jazyka C jako inkrement (a++, ++a). Umocňování se značí stříškou (a^b) a pro celočíselné dělení a modulo žádné zkrácené zápisy neexistují a lze místo nich použít funkce Quotient a Mod. Znak násobení * lze vynechat, mezery se tak vyhodnocují automaticky jako násobení[44][pozn. 9].

Vektorový součin odpovídá funkci Cross, maticové násobení odpovídá funkci Dot a zapisuje se tečkou (a . b). Vynásobení vektoru či matice číslem se provádí po prvcích a tak např. 3 * {a, b, c} vrátí {3 a, 3 b, 3 c}. Podobně se násobení chová i při (skalárním) násobení matice vektorem: {a, b, c} * {{1, 2}, {3, 4}, {5, 6}} vrátí {{a, 2 a}, {3 b, 4 b}, {5 c, 6 c}}, zatímco maticové vynásobení {a, b, c} . {{1, 2}, {3, 4}, {5, 6}} vrátí {a + 3 b + 5 c, 2 a + 4 b + 6 c}.

Kromě tradičních operátorů obsahuje WL i množství operátorů bez předdefinovaného chování. Jedním takovým je NonCommutativeMultiply[45], jenž lze zapsat jako dvě hvězdičky **. Pomocí UpValues lze tomuto operátoru dodefinovat aritmetická pravidla, podle kterých se má chovat. Konstrukt a ** b tak poté třeba může představovat nekomutativní součin proměnných a a b.

Přiřazení[editovat | editovat zdroj]

WL nabízí dva druhy přiřazení — přímé (striktní, výraz Set) a odložené (nestriktní, výraz SetDelayed)[46]. Při přímém přiřazení je příkazem var = hod do proměnné var na levé straně přiřazena aktuální hodnota hod na straně pravé. Naproti tomu odložené přiřazení var := hod hodnotu na pravé straně nevyhodnocuje až do chvíle, kdy je proměnná volána. Rozdíl mezi těmito dvěma přiřazeními je dobře patrný, je-li do proměnné přiřazena náhodná hodnota funkcí RandomReal a tato proměnná je následně několikrát po sobě volána:[pozn. 10]

x = RandomReal[];
y := RandomReal[];
{x, y} (* vrátí {0.211393, 0.882601} *)
{x, y} (* vrátí {0.211393, 0.303523} *)
{x, y} (* vrátí {0.211393, 0.196294} *)

Přímé přiřazení se používá pro definici konstant a proměnných, odložené přiřazení se pak běžně využívá při definicích funkcí. Viz též sekci „Funkce“.

Přiřazení lze i řetězit a tak lze psát např. a = b = c = 42. Lze přiřazovat i do několika proměnných současně pomocí seznamů: {a, b, c} = {1, 2, 3}. Tímto způsobem lze přehodit hodnoty dvou proměnných: {a, b} = {b, a}[47]. Podporovány jsou i kombinace aritmetických operací s přiřazením ve stypu jazyka C: +=, *=, /=, atd.[48]

Porovnávání[editovat | editovat zdroj]

WL obsahuje tradiční porovnávací operátory jako „větší než“ (>), „menší než“ (<), „větší nebo rovno“ (>=) a „menší nebo rovno“ (<=)[49]. Tyto vztahy odpovídají po řadě funkcím Less, LessEqual, Greater a GreaterEqual. Vztah „rovná se“ se zapisuje dvěma rovnítky (==, funkce Equal) a vztah „nerovná se“ se zapisuje vykřičníkem následovným rovnítkem (!=, funkce Unequal). Všechny následující výrazy jsou vyhodnoceny jako pravdivé:

3 > 2; -1 < 0; 2 >= 2; 1 <= 4.5;
1 < 3 < 12.3 (* jsou podporována i zřetězená porovnání *)

Kromě testu na rovnost poskytuje WL i test na identitu[50], jenž se zapisuje třemi rovnítky (===, funkce SameQ) a jehož opak je vyjádřen symbolem =!= a funkcí UnsameQ. Zatímco rovnost == testuje, zda jsou si dvě čísla numericky rovna, identita === zjišťuje, zda se jedná o skutečně stejná čísla. Tak například výraz 2 == 2.0 vrátí True, protože celé číslo 2 typu Integer je numericky rovno reálnému číslu 2.0 typu Real, avšak 2 === 2.0 vrací False, protože se jedná o dva různé typy. Obdobně, máme-li dvě proměnné x a y, jimž nebyly dosud přiřazeny žádné hodnoty, tak výraz x == y zůstane nevyhodnocen, protože nelze určit, zda si dvě hodnoty jsou rovny, zatímco x === y vrátí rovnou False.

Kromě výše uvedených funkcí jako Equal či Greater, které berou dva parametry, poskytuje WL i jejich operátorové podoby[51], kde je dosazen pouze parametr první. Místo zápisu Equal[x, y] (jenž je ekvivalentní zápisu x == y) lze psát EqualTo[x][y], kde EqualTo je operátorová obdoba funkce Equal. Výraz EqualTo[x][y] je nutno číst jako funkci EqualTo[x] (parametrizovanou proměnnou x) aplikovanou na proměnnou y. Operátorové podoby srovnávacích funkcí lze například využít ve chvíli, kde chceme porovnávat celé pole čísel s jednou jedinou hodnotou. Tak například:

EqualTo[3] /@ {1, 2, 3, 4, 5, 6} (* vrátí {False, False, True, False, False, False} *)
GreaterThan[3] /@ {1, 2, 3, 4, 5, 6} (* vrátí {False, False, False, True, True, True} *)

kde GreaterThan je operátorová forma funkce Greater.

Logické operátory[editovat | editovat zdroj]

Pravdivostní hodnoty pravda a nepravda jsou představovány konstantami True a False. Základní logické operace jsou pak zadány těmito funkcemi[52]: konjunkce pomocí And (místo And[a, b] lze psát též a && b), disjunkce pomocí Or (a || b) a negace pomocí Not (!a)[pozn. 11]. Funkce And a Or jsou vyhodnocovány zkráceně a tak je-li výsledná pravdivostní hodnota známa dříve, než se vyhodnotí všechny výrazy, nejsou tyto vyhodnoceny. Podporovány jsou i další logické operace jako Xor, Nand, Implies, atd. Ve WL neexistují speciální znaky pro bitové logické operace a je třeba použít názvy odpovídajících funkcí jako BitAnd, BitOr, BitNot, atd.[53]

WL podporuje i kvantifikátory pro všechny (ForAll) a existuje (Exists)[54]. Komplikované logické výrazy lze zjednodušit pomocí funkcí Resolve, BooleanConvert či Simplify. Některé výrazy nelze vyhodnotit ani jako pravdu či nepravdu. Takové výrazy jsou programem posílány nevyhodnocené. Chceme-li vynutit jejich vyhodnocení (na False v případě nerozhodnutelných výrazů), lze je obalit do funkce TrueQ. Pro převod pravdivostní hodnoty na číslo lze použít funkci Boole, která převede True na 1 a False na 0. Ve WL neexistuje datový typ odpovídající typu bool či boolean z jiných programovacích jazyků a pokud je třeba specifikovat, že daná proměnná var nabývá pouze pravdivostních hodnot, lze psát Element[var, True|False].

Řídicí struktury[editovat | editovat zdroj]

Podmínky[editovat | editovat zdroj]

Podmínky lze implementovat různými způsoby[55]. Nejčastějším je patrně konstrukt If[56], jehož základní syntaxe zní If[podm, vyraz1, vyraz2], kde podm je podmínka, která je buď pravda (True), v kterémžto případě se vyhodnotí vyraz1 či nepravda (False), v kterémžto případě se vyhodnotí vyraz2. Např.

x = 2;
If[x < 1, y = 3, y = 5];
y (* vrátí 5 *)

Podmínky jsou na rozdíl od populárních jazyků jako C či Python představovány výrazem, který lze vyhodnotit. Lze tak předchozí kód přepsat do tvaru

x = 2;
y = If[x < 1, 3, 5];
y (* vrátí 5 *)

Na rozdíl od některých jiných jazyků, If má tři argumenty, přičemž třetí argument je vyhodnocen, nelze-li určit pravdivostní hodnotu prvního argumentu. Pro příklad uvažme, že proměnná x nemá přiřazenu žádnou hodnotu a nelze tak určit, zda je menší nebo větší než jedna:

y = If[x < 1, 3, 5, "nevím"];
y (* vrátí "nevím" *)

Řetěz If výrazů lze nahradit funkcí Switch[57], podobně jako v jiných jazycích, jejíž syntaxe zní Switch[vstup, vzor1, vyraz1, vzor2, vyraz2, ..., vzorN, vyrazN]. První argument vstup je vyhodnocen a výsledná hodnota je porovnávána postupně s výrazy vzor1, vzor2, atd. Ve chvíli, kdy je nalezena shoda mezi hodnotou vstup a jistým vzorem vzorj, je vyhodnocen kód vyrazj a běh programu je poté přenesen za konec výrazu Switch. Jako vzor1vzorN lze použít obecné vzory a není tedy nutná přesná shoda mezi vzorj a vstupní hodnotou. Roli výchozího chování, které je např. v jazyce Java umožněno klíčových slovem default, plní vzor _, který lze umístit na pozici argumentu vzorN. Chceme-li tedy například udat slovní hodnocení na základě školní známky s tím, že pro známky mimo rozsah vypíšeme chybovou hlášku, můžeme psát:

Switch[znamka,
    1, "výborně",
    2, "chvalitebně",
    3|4|5, "příště se lépe připrav",
    _, "neplatná známka"
]

V případě, že znamka je 3 nebo 4 nebo 5 vrátí Switch jako návratovou hodnotu řetězec "příště se lépe připrav". Pokud není známka celé číslo mezi 1 a 5, tak Switch vrátí řetězec "neplatná známka".

Ve WL existuje i funkce Which[58] se syntaxí Which[podm1, vyraz1, podm2, vyraz2, ..., podmN, vyrazN], ve které dochází postupně k vyhodnocování podmínek podm1, podm2, atd. a ve chvíli, kdy je daná podmínka podmj vyhodnocena jako True, tak se provede za ní specifikovaný kód vyrazj. Roli klíčového slova default zde pak může plnit literál True vložený jako poslední podmínka podmN. Chceme-li tedy například určit denní dobu v závislosti na hodině zadané v proměnné hod a současně vrátit chybové hlášení v případě, že hod není v rozmezí 0-24, můžeme psát:

Which[
    0<=hod<12, "před polednem",
    hod==12, "v poledne",
    12<hod<=24, "po poledni",
    True, "hod mimo rozsah"
]

Cykly a jejich ekvivalenty[editovat | editovat zdroj]

WL nabízí cykly typické pro další programovací jazyky, jako for cyklus (For), while cyklus (While) a do-while cyklus (reprezentovaný příkazem Until uvedeným ve verzi 13.1)[59]. Syntaxe for cyklu je velmi blízká syntaxi pro tento cyklus v jazyce C (konkrétně For[počátek, konec, inkrement, tělo][60]). Používat tento příkaz se nicméně nedoporučuje[61] a místo toho je upřednostňováno používání specializovanějších příkazů[62], z nichž některé jsou uvedeny níže.

Je-li cílem provést tutéž akci pro předem daný počet indexů, lze použít funkci Do, jejíž syntaxe zní Do[...kód potenciálně závisející na i..., {i, start, konec}][63]. Pokud se argument start vynechá, index i jde od jedničky. Vypsání tří po sobě jdoucích čísel 1, 2, 3 tak lze provést kódem Do[Print[i], {i, 3}]. Je-li naopak cílem vytvořit pole hodnot na základě jistého předpisu, lze použít příkaz Table nebo Array, jejichž použití zní:

Table[a[i], {i, 3}] (* vrátí: {a[1], a[2], a[3]} *)
Array[a, {3}] (* vrátí: {a[1], a[2], a[3]} *)

Funkce Table umožňuje místo indexu coby číselného pořadí použít přímo prvky pole a napodobuje tak chování konstruktu foreach z jiných jazyků. Srovnej:

seznam = {"a", "b", "c"};
Table[str<>"x", {str, seznam}] (* vrátí: {"ax", "bx", "cx"} *)

Vícerozměrná pole lze vytvořit příkazem Table, kde je uveden příslušný počet indexových proměnných s odpovídajícími rozsahy[64]. Například:

Table[a[i, j], {i, 2}, {j, -1, 1}]
(* vrátí: {{a[1, -1], a[1, 0], a[1, 1]}, {a[2, -1], a[2, 0], a[2, 1]}} *)

Poznamenejme, že místo příkazu Do lze použít funkci Scan a podobně místo Table lze použít funkci Map. Výše uvedený příklad lze přepsat do tvaru:

Map[a, Range[3]] (* vrátí: {a[1], a[2], a[3]} *)
a /@ Range[3] (* vrátí: {a[1], a[2], a[3]} *)

kde Range[n] vrací pole čísel tvaru {1, 2, 3, ..., n}. Druhý řádek je pouze kompaktní zápis řádku prvního, se kterým je ekvivalentní[65]. Používáním funkce Map lze elegantně provádět stejné operace jako s Table s tou výhodou, že není třeba používat explicitně indexovou proměnnou.

Další častou situací je, když je cyklus použit pro opakovanou aplikaci téže funkce na jistou počáteční hodnotu[66]. Tento případ lze ve WL řešit použitím funkce Nest, jejíž první parametr udává funkci, jež má být aplikována, druhý parametr udává počáteční hodnotu a parametr třetí pak počet opakování:

Nest[f, x, 3] (* vrátí: f[f[f[x]]] *)

Potřebujeme-li v každém opakování zvolit dodatečnou hodnotu, lze místo Nest použít funkci Fold, jejíž první parametr je aplikovaná funkce, parametr druhý je počáteční hodnota a parametr třetí je seznam dodatečných hodnot

Fold[f, x, {a, b, c}] (* vrátí: f[f[f[x, a], b], c] *)

Výjimky[editovat | editovat zdroj]

Vyhodnocování kódu lze programově dočasně přerušit funkcí Interrupt, která vyvolá dialogové okno, v němž může uživatel určit, jak dále postupovat. Ukončit okamžitě vyhodnocování lze programově funkcí Abort, jež vrátí hodnotu $Aborted. Některé funkce při nesplnění očekávané akce vrátí $Failed. Přerušit standardní tok vyhodnocování příkazů lze vložením výrazu Throw na dané místo kódu. Tento výraz musí být posléze zachycen funkcí Catch, do níž je zabalen dotčený kód[67], viz např.:

Catch[prikaz1; prikaz2; Throw[aha]; prikaz3] (* vrátí: aha *)

Kód může vracet i zprávy příkazem Message[68]. Tyto zprávy mohou být zachycovány funkcí Check. Zpráva pro daný symbol f se specifikuje syntaxí f::jmenozpravy = "text zprávy". Šíření dané zprávy z konkrétního výrazu lze potlačit pomocí funkce Quiet, potlačení zprávy či skupiny zpráv v rámci celého systému lze funkcí Off a její znovuzprovoznění lze provést funkcí On. Srovnej funkci:

deleni::delnul = "Dělení nulou"; (* definice chybové zprávy *)
deleni[a_, b_] := If[b != 0, a/b, Message[deleni::delnul];$Failed]; (* definice funkce *)

a její volání pro různé vstupní hodnoty:

deleni[3, 2] (* vrátí: 3/2 *)
deleni[3, 0] (* vypíše chybovou hlášku "Dělení nulou" a vrátí: $Failed *)
Quiet[deleni[3, 0]] (* nevypíše chybovou hlášku a vrátí: $Failed *)
Check[deleni[3, 0], "příště neděl nulou"] (* vypíše chybovou hlášku "Dělení nulou" a vrátí: "příště neděl nulou" *)

Použít lze i funkci Assert, která vyvolá chybovou zprávu ve chvíli, kdy podmínka specifikovaná uvnitř Assert nevrátí True. Pro zjišťování hodnot proměnných a výrazů uvnitř větších bloků kódu lze užít funkci Echo a její příbuzné[69][70].

Ve verzi 12.2 byla zavedena modernější sada funkcí[71] v čele s funkcemi Confirm a Enclose. Tyto funkce při neúspěchu vrátí výraz Failure, jehož tělo obsahuje doplňující informace o chybě[pozn. 12]. Funkci deleni z příkladu výše lze s pomocí funkcí ConfirmBy a Enclose přepsat do tvaru

deleni[a_, b_] := Enclose[a/ConfirmBy[b, # != 0 &, "Dělení nulou"]] (* definice funkce spolu s chybovým hlášením *)
deleni[3, 2] (* vrátí: 3/2 *)
deleni[3, 0] (* vrátí: Failure[...], jenž obsahuje doplňující informace o chybě včetně hlášky "Dělení nulou" *)

Vzory a nahrazovací pravidla[editovat | editovat zdroj]

Vzory[editovat | editovat zdroj]

Jedním ze specifik WL je podpora široké škály vzorů (angl. patterns)[72], což jsou svým způsobem prototypy výrazů a lze je chápat jako regulární výrazy aplikované na kód a data kódem zpracovávaná. S jejich pomocí lze vyhledávat části kódu či zpracovávaných dat a nahrazovat tyto kódem jiným.

Například podtržítko _ označuje libovolný výraz, dvě podtržítka __ označují posloupnost jednoho a více výrazů a tři podtržítka ___ označují posloupnost libovolného nezáporného počtu výrazů[73]. Tyto a podobné vzory lze použít například při zjišťování, zda daný výraz vyhovuje jistým podmínkám, či k provádění úprav dat způsobem, který připomíná práci funkcí. Pokud chceme například zjistit, zda je zadaný seznam sez neprázdný, lze toto provést voláním MatchQ[sez, {__}], kde vzor {__} označuje seznam s alespoň jedním prvkem a funkce MatchQ zjišťuje, zda daný výraz, zde sez, vyhovuje danému vzoru.

Každý výraz ve WL má hlavičku. Tuto lze specifikovat připojením jejího názvu za podtržítko[74]. Chceme-li tedy zjistit, zda daný seznam sez obsahuje pouze reálná čísla, lze toto provést voláním MatchQ[sez, {___Real}], kde ___Real označuje posloupnost libovolného počtu reálných čísel. Části vzoru lze i přiřadit jméno, což je výhodné při použití v pravidlech a definicích funkcí. Funkce se běžně definují způsobem: f[x_] := (nějaký kód závislý na x), kde konstrukt x_ je vzor označující libovolný výraz, jemuž je přiřazeno jméno x. V případě složitějších vzorů lze použít místo podtržítek tečky a jméno se pak udává volitelně před dvojtečku[75]. Například konstrukt x:({a, b}..) označuje vzor pojmenovaný x, který odpovídá posloupnosti jednoho či více seznamů tvaru {a, b}.

Množinu výrazů vyhovujících danému vzoru lze úžeji specifikovat pomocí podmínek (Condition) a testovacích funkcí (PatternTest)[76]. Například vzor x_List/;Length[x]<=5 označuje seznam s nanejvýš pěti prvky. Tento vzor je tvaru vzor/;podminka, kde podminka je výraz, který musí vrátit True či False. Alternativou je použití testovací funkce. Předchozí vzor lze ekvivalentně přepsat do tvaru x_List?(Length[#]<=5&), jenž je tvaru vzor?test, kde test je funkce, která po aplikování na vzor musí vrátit True či False. Podobně lze postupovat i když místo ryzí funkce použijeme funkci standardní. Například vzor a_?EvenQ označuje libovolný výraz, pro nějž funkce EvenQ vrátí True. Vzhledem k tomu, že EvenQ testuje, kde je vstupní parameter sudé číslo, označuje tento vzor tedy sudé číslo.

Vzory jsou podporovány mnoha funkcemi jako Switch při porovnávání jednotlivých případů se vstupní hodnotou, Cases pro výběr prvků ze seznamu, které splňují dodatečná kriteria atd.[77]

Pravidla[editovat | editovat zdroj]

WL umožňuje práci s nahrazovacími pravidly (angl. rules, popř. transformation rules)[78], díky nimž lze nahradit část výrazu výrazem jiným. Máme-li například seznam tvaru {a, 2, a, 3}, který chceme změnit do tvaru {1, 2, 1, 3}, můžeme toto provést voláním

{a, 2, a, 3} /. a->1 (* vrátí: {1, 2, 1, 3} *)

kde a->1 je pravidlo, které udává, že každý výskyt výrazu a se má nahradit číslem 1. Podobně jako v případě přiřazení, existuje i přímé a odložené pravidlo. Přímé pravidlo (Rule, zkráceně ->) vyhodnotí pravou stranu přiřazení ve chvíli, kdy je toto pravidlo definováno, zatímco odložené pravidlo (RuleDelayed, zkráceně :>) vyhodnotí pravou stranu až ve chvíli volání[79]. Srovnej:

{a, a, a} /. a->RandomReal[] (* vrátí: {0.209308, 0.2093080, 0.209308} *)
{a, a, a} /. a:>RandomReal[] (* vrátí: {0.827961, 0.0109041, 0.161149} *)

Jak levá, tak pravá strana pravidla může mít velmi komplikovanou strukturu založenou na vzorech. Toto lze efektivně využít například ve chvíli, kdy nelze dopředu určit, čím se má daný výraz nahradit, protože jeho tvar závisí na tvaru nahrazované hodnoty. Srovnej následující kód:

{x, 10, 3., 1, 2, -2} /. a_Integer?(#>1&):>ToString[a+1]<>" atd."
(* vrátí: {x, "11 atd.", 3., 1, "3 atd.", -2} *)

Tento kód vyhledá v seznamu všechny výskyty celých čísel větších než jedna a nahradí je řetězcem, který obsahuje číslo o jedno větší s dodatkem " atd.".

Syntax vyraz /. a->b je ekvivalentní zápisu ReplaceAll[vyraz, a->b], což je dále ekvivalentní zápisu ReplaceAll[vyraz, Rule[a, b]]. Konstrukt a->b samotný žádné nahrazování neprovádí, jedná se pouze o recept, jak se má nahrazení provést. Samotné provedení má ale na starosti funkce ReplaceAll a jí příbuzné funkce jako ReplaceRepeated (zkráceně //.)[80].

Blokové struktury[editovat | editovat zdroj]

Základními blokovými strukturami jsou ve WL konstrukty Block, Module a With, z nichž má každý trochu jinou funkcionalitu[81][82], jak popsáno níže.

Block[editovat | editovat zdroj]

Block provádí dynamic scoping, kde se při provádění bloku dočasně přepíše hodnota dané proměnné. Syntaxe zní Block[{var1, var2, ..., varN}, telo], kde var1 atd. jsou lokální proměnné a telo je blok kódu. Proměnné lze rovnou i inicializovat a psát Block[{var1 = hod1, var2 = hod2, ..., varN = hodN}, telo][83], přičemž inicializovány nemusejí být všechny. Uvažme následující příklad:

a = 42;
Block[{a, b = 3, c},
    a = b;
    Print["uvnitr Block: ", a, " ... ", c];
];
Print[a];

Tento kód vypíše:

uvnitr Block: 3 ... c
42

Uvnitř Block můžeme přiřazovat do lokálních proměnných, viz příkaz a = b výše. Pokud nemá daná lokální proměnná přiřazenu hodnotu, je vrácena jako symbol, viz řádek "uvnitr Block: 3 ... c" ve výpisu. Vzhledem ke způsobu lokalizace v Block není třeba, aby lokální proměnná byla explicitně zmíněna v těle, srovnej následující kód:

b := a + 1 (* odložené přiřazení do proměnné b *)
a = 2; (* globální hodnota proměnné a *)
Block[{a = 5}, b] (* vrátí: 6 *)
b (* vrátí: 3 *)

Module[editovat | editovat zdroj]

Module provádí lexical scoping, kde jsou proměnné interně přejmenovávány tak, že mají unikátní název, přičemž jejich viditelnost není omezena na tělo bloku. Syntaxe je zcela analogická té pro Block[84]. Pro srovnání s Block[85] uvažme kód:

a = 42;
Module[{a, b = 3, c},
    a = b;
    Print["uvnitr Module: ", a, " ... ", c];
];
Print[a];

jenž vypíše:

uvnitr Module: 3 ... c$65048
42

Jak vidno, lokální proměnná c má pozměněné jméno[pozn. 13]. Tímto způsobem je možné, na rozdíl od Block, použít původně lokální proměnnou i po skončení bloku Module. Pro ilustraci uvažme následující kód, kde je v těle Module definována funkce f a tato je posléze vrácena:

Module[{f}, f[x_] := x^2; f] (* vrátí: f$65834 *)
f$65834[y] (* vrátí y^2 *)

Původně lokální proměnná f je přejmenována na f$65834 a jako takovou ji lze použít i vně Module.

With[editovat | editovat zdroj]

With provádí lokalizaci konstant, to jest proměnných, jimž nelze po zbytek bloku měnit hodnotu[87]. Nelze tak do takových proměnných přiřazovat, na rozdíl od Block a Module. Syntaxe je opět zcela analogická té pro Block s tím, že každou lokální proměnnou je nutno inicializovat, srovnej kód:

a = 42;
With[{a = 3},
    Print["uvnitr With: ", a];
];
Print[a];

jež vypíše:

uvnitr With: 3
42

Blok With je v mnoha ohledech spíše než bloku Block podobný substitučním funkcím jako ReplaceAll. Na rozdíl od nich substituce neprobíhá po vyhodnocení výrazu, ale před ním[88], srovnej:

f[x_] := If[x < 1, "maly", "velky", x]; (* definice funkce f *)
With[{x = 2}, f[x]] (* vrátí: "velky" *)
f[x] /. x->2 (* vrátí: 2 *)

Na prvním řádku je definována funkce f, která vrátí buď "maly", je-li vstupní parametr menší než 1, anebo "velky", je-li parametr větší než 1. V případě, že vstupní parametr nemá přiřazenu žádnou hodnotu, vrátí funkce f tento parametr nevyhodnocený. Na druhém řádku je v bloku With do proměnné x přiřazena hodnota 2 a tato je posléze poslána do funkce f. Na třetím řádku je obdobná situace, kde se použije substituční pravidlo, kterým se parametr x nahradí hodnotou 2. Tato substituce ale na rozdíl od druhého řádku probíhá až po vyhodnocení funkce f, čímž pádem obdržíme jiný výsledek.

Strukturování kódu[editovat | editovat zdroj]

Související informace naleznete také v článku Mathematica#Strukturování kódu.

Jmenné prostory[editovat | editovat zdroj]

Každý symbol ve WL je součástí nějakého jmenného prostoru, kterým se ve WL říká kontexty (angl. contexts)[89]. Základním kontextem pro předdefinované symboly je System, výchozím kontextem pro uživatelem definované symboly je pak Global. Stejně pojmenované symboly ve dvou různých noteboocích či buňkách lze lokalizovat tím, že se jim přiřadí kontext jedinečný pro daný notebook či buňku[90]. Definovat lze i vlastní kontexty. Symbol x s explicitně vypsaným kontextem mujkontext se udává kódem mujkontext`x, kde ` je zpětný apostrof. Kontexty lze i vnořovat a psát tak např. nadkontext`podkontext`x. Aktuální kontext je uložen v proměnné $Context, zjistit kontext daného symbolu lze funkcí Context. Funkce Contexts vrací seznam všech dostupných kontextů a proměnná $ContextPath obsahuje seznam kontextů, které jsou prohledávány při hledání definice pro zadaný symbol. Každý balík definuje nový kontext a při nahrání balíku funkcí Needs je tento kontext vložen do proměnné $Packages. Po nahrání balíku není nutné explicitně vypisovat u každého symbolu jeho kontext.

Vypsat všechny symboly v daném kontextu lze příkazem ?jmenokontextu`*, kde jmenokontextu je jméno daného kontextu. Vypsat všechny symboly definované uživatelem v daném běhu jádra tak lze voláním ?Global`*. Viz též oddíl „Nápověda“.

Balíky[editovat | editovat zdroj]

Související informace naleznete také v článku Mathematica#Interní struktura balíku.

Balíky (angl. packages) jsou ucelené kusy kódu zabaleného do kontextu a uložené v samostatném souboru s příponou .wl[91]. Kód balíku začíná výrazem BeginPackage a končí výrazem EndPackage. Funkce a proměnné, které jsou používány pouze uvnitř balíku a které nemají být přímo přístupny uživateli balíku, lze vložit mezi výrazy Begin a End. Typický balík má následující strukturu[92]:

BeginPackage["NovyKontext`"] (* počátek balíku a definice kontextu *)

novaFunkce::usage = "Dokumentační řetězec nové funkce."; (* tím, že funkci uvedeme před příkazem Begin, zajistíme, že je viditelná po načtení balíku uživateli *)

Begin["`Private`"] (* počátek části kódu, jež není přímo přístupná uživateli *)

novaFunkce[x_] := interniFunkce[x]^2 (* definice funkce *)
interniFunkce[x_] := x + 1 (* tato funkce není viditelná uživateli *)

End[] (* konec interních definic *)

EndPackage[] (* konec balíku *)

Balík funkcí lze načíst buď pomocí funkce Get, jež vyhodnotí kód v balíku při každém volání této funkce, nebo funkcí Needs, která vyhodnotí kód balíku jen při prvním volání. Externí programy, jež dokážou komunikovat s jádrem protokolem WSTP, lze propojit s jádrem pomocí funkce Install. Dynamické knihovny lze nahrát přímo do výpočetního jádra voláním funkce LibraryLoad a příbuzných funkcí[93].

Paclety[editovat | editovat zdroj]

Nadstavbou balíků jsou paclety (angl. paclets)[94], což jsou v podstatě archivy, jež mohou obsahovat řadu balíků s kódem ve WL i jiných programovacích jazycích, dokumentaci, dynamické knihovny či stylopisy. Paclet se z obyčejného archivu stane tím, že se do archivu vloží soubor s názvem PacletInfo.wl, jež obsahuje výraz s hlavičkou PacletObject (do verze 12.1 s hlavičkou Paclet), jež obsahuje metadata o souborech v archivu obsažených. Paclety nabízejí širší funkcionalitu než balíky a je nutné je do výpočetního systému nejdříve nainstalovat funkcí PacletInstall. Od verze 12.1 lze paclety centrálně ukládat do online repozitáře[95].

Funkce[editovat | editovat zdroj]

Základní použití[editovat | editovat zdroj]

Funkce lze volat pomocí jednoduchých hranatých závorek, do nichž jsou vepsány vstupní parametry, např.: Sin[0.9], Table[i,{i,3}] či f[3] pro uživatelem definovanou funkci f[41]. Základní tvar definice funkce jedné proměnné vypadá následovně:

f[x_] := x^2

kde na levé straně je výraz tvaru jmenofunkce[vstup_] a na pravé straně odloženého přiřazení je tělo funkce zpracovávající vstup. Je-li potřeba při výpočtu použít dodatečné proměnné, lze tyto lokalizovat pomocí bloků Block, With či Module:

f[x_] := Module[{y}, (* lokální proměnná y *)
    y = x^2;
    y + 1 (* popř. Return[y + 1]; *)
]

Všimněme si, že není nutno použít příkaz Return, protože blok vrací automaticky hodnotu na posledním řádku.[pozn. 14]

Funkce jsou first-class objekty a tak lze s nimi nakládat stejně jako s proměnnými, srovnej:

fun = Cos;
If[podm, fun = Sin];
fun[0.2]

Tento kód aplikuje na číslo buď cosinus, anebo sinus v závislosti na pravdivostní hodnotě proměnné podm.

Definice[editovat | editovat zdroj]

Přetěžování a polymorfizmus[editovat | editovat zdroj]

Při definici funkce lze uplatnit širokou paletu vzorů, které specifikují, v jakých případech má být daná definice použita. Jedné funkci lze přiřadit vícero definic pro různé druhy vstupů a WL tak umožňuje přetěžování a polymorfizmus[96]. Pokud danému vstupu nevyhovuje ani jedna definice, zůstává volaný výraz nevyhodnocen. Pokud naopak danému vstupu vyhovuje více definic, je použita ta, která je nejspecifičtější. Srovnej:

f[x_] := x^2 (* funkce f jedné proměnné *)
f[x_, y_] :=  x + y (* tatáž funkce, ale definována pro dva vstupní parametry *)
f[x_, y_?EvenQ] := "sude cislo na vstupu" (* opět tatáž funkce, ale nyní je její akce definována pro případy, kdy je druhý vstup sudé číslo *)

Voláme-li tuto funkci f na různé vstupy, můžeme obdržet:

f[4] (* vrátí: 16 *)
f[4, 2] (* vrátí: "sude cislo na vstupu" *)
f[4, 3] (* vrátí: 7 *)
f[4, 3, 7] (* vrátí: f[4, 3, 7] *)

Podporovány jsou i složitější vzory[97]. Například následující funkce vypíše číslo 1 tehdy, kdy je první vstup kladný a druhý vstup je větší než ten první. Ve všech ostatních případech vypíše 0:

f[x_?Positive, y_]/;(y > x) := 1
f[_, _] := 0

Vstupní a výchozí hodnoty[editovat | editovat zdroj]

Vstupním parametrům lze zadávat výchozí hodnoty a to dvěma způsoby. Buď pomocí výrazu Default, anebo syntaxí používající dvojtečku v definici funkce[98]:

Default[f] = 3; (* výchozí hodnota parametru funkce f je 3 *)
f[x_.] := x + 1 (* aby byla použita výchozí hodnota, je nutno ke vzoru x_ připojit tečku *)
g[x_ : 3] := x + 1 (* ekvivalentní definice pomocí dvojtečky *)
f[] (* vrátí: 4 *)
g[] (* vrátí: 4 *)

Lze navíc i omezit obor možných vstupních hodnot tím, že se specifikuje podmínka[97], kterou musí vstupní parametr splňovat. Například následujícím kódem lze definovat funkci h, která pro sudé číslo vrátí číslo o jedna menší, pro liché číslo zůstane nevyhodnocena a pokud není zadán žádný vstup, použije se automaticky hodnota vstupu rovná 2:

h[x : _?EvenQ : 2] := x - 1 (* h[vstup : podminka : vychoziHodnota] := atd. *)
h[1] (* vrátí: h[1] *)
h[2] (* vrátí: 1 *)
h[] (* vrátí: 1 *)

Druhy přiřazení[editovat | editovat zdroj]

Při definicích funkcí je nutné dbát rozdílu mezi přímým a odloženým přiřazením[99], viz sekci „Přiřazení“. Srovnej následující tři definice, kde jsme nejdříve do globální proměnné x uložili hodnotu 5:

f1[x] = x^2; (* bez vzoru a odloženého přiřazení *)
f2[x_] = x^2; (* vzor a přímé přiřazení *)
f3[x_] := x^2; (* vzor a odložené přiřazení *)
{f1[y], f2[y], f3[y]} (* vrátí: {f1[y], 25, y^2}  *)

V prvním řádku se při definici funkce f1 použije hodnota globální proměnné x, to jest 5, a první řádek tak odpovídá přiřazení f1[5] = 25. Funkce f1 tak má definovanou hodnotu jen pro jeden jediný vstup a tím je číslo 5. Ve druhém řádku je v hlavičce funkce použit vzor x_, na pravé straně přiřazení ale vystupuje opět globální proměnná, jež je umocněna na druhou. Druhý řádek tak odpovídá situaci, kde funkce f2 pro jakýkoliv vstup vrátí hodnotu 25. Třetí řádek používá jak vzor x_, tak odložené přiřazení, které propojí hodnotu vzoru na levé straně se symbolem x na straně pravé. Tato poslední definice se chová očekávaným způsobem.

Ačkoli je třeba obyčejně používat odložené přiřazení, jak plyne z předchozího odstavce, někdy je přeci jen výhodné použít přiřazení přímé. A to v případě, kdy je vhodné definovat hodnotu funkce pro konkrétní hodnoty vstupů. Chceme-li například ručně definovat funkci sinc, jež je pro nenulová dána vztahem , přičemž pro nulové dodefinovat [pozn. 15], lze toto učinit následujícím kódem:

sinc[x_] := Sin[x]/x;
sinc[0] = 1;

Výpočetní systém rozpozná, že definice na druhém řádku je specifičtější než ta na řádku prvním[100] a při volání sinc[0] je tak aplikována jako první, čímž obdržíme správný výsledek 1. Alternativním způsobem k výše uvedené definici je použití funkce Piecewise:

sinc[x_] := Piecewise[{{Sin[x]/x, x != 0}}, 1]

Memoizace[editovat | editovat zdroj]

Někdy je výpočet hodnoty dané funkce na konkrétní vstup náročný a zdlouhavý. Pokud se tento výpočet v kódu opakuje, lze jeho výsledek dynamicky uložit jako součást definice dané funkce metodou zvanou memoizace. Mějme funkci f, jejíž definice zní f[x_] := (tělo funkce). Pokud místo tohoto zápisu užijeme zápisu[101]:

f[x_] := f[x] = (tělo funkce)

dojde při každém volání funkce k vyhodnocení jejího těla pro konkrétní vstup, třeba 32, a výsledek je uložen do výrazu f[32], který se tak stává součástí definice funkce f. Takto lze dynamicky během běhu kódu měnit definice funkcí i jiných objektů. Viz příklady „Fibonacciho posloupnost“ a „Faktoriál“ v článku Wolfram Language.

Třídy funkcí a uzávěry[editovat | editovat zdroj]

Lze vytvářet i konstrukty s více než jen jednou hranatou závorkou, např. g[x_][y_] := y^x. Takto definovanou funkci lze chápat jako celou třídu funkcí, kde první vstup hraje roli parametru, jež rozlišuje mezi jednotlivými funkcemi dané třídy. Výraz g[2] není vyhodnocen až do chvíle, než je aplikován na nějaký vstup a lze ho chápat jako operátor druhé mocniny, protože f[2][x] vrátí x^2.

Podobně se chovají funkce implementované pomocí Module[82], které vracejí jako hodnotu jinou funkci. Je-li při definici vnitřní funkce použit vstupní parametr funkce vnější, je tento parametr držen v definici vnitřní funkce i po opuštění těla funkce vnější[pozn. 16]:

f[x_] := Module[{k}, (* uzávěr *)
   k[y_] := x + y; (* definuj lokálně funkci k *)
   k (* vrať funkci s uloženou hodnotou proměnné x *)
]
g = f[3]; (* vrátí funkci, která ke vstupu přičítá 3 *)
g[5] (* vrátí: 8 *)

Ryzí funkce[editovat | editovat zdroj]

WL podporuje anonymní funkce, které nazývá ryzí funkce (angl. pure functions)[102]. Tyto funkce jsou reprezentovány jako výrazy s hlavičkou Function, běžně se ale zapisují následující notací:

(výraz obsahující symbol #) &

Symbol # (neboli Slot) představuje vstupní parametr a ampersand na konci určuje, že se jedná o ryzí funkci. Pokud je vstupních parametrů více, lze každému slotu udělit číslo[pozn. 17], viz například:

(#1 + #2) & (* součet dvou vstupů *)

Pokud není třeba přistupovat ke každému vstupu zvlášť, lze použít zápis ##n, který představuje všechny vstupy od n-tého počínaje[102]. Pokud jsou vstupními parametry klíče asociativního pole, lze sloty pojmenovat:

asoc = <|"jmeno"->"Alik", "vek"->15|>;
(#jmeno <> "u")&[asoc] (* vrátí: "Aliku" *)

Ryzí funkci lze definovat i následujícím způsobem známým z matematiky[41][pozn. 18]:

x |-> (výraz obsahující symbol x)

kde místo slotů použijeme pojmenované parametry. Tato syntaxe definuje funkci. Chceme-li tuto pojmenovat pro pozdější použití, lze to učinit standardním přiřazením:

druhaMocnina = x |-> x^2; (* definice *)
druhaMocnina[3] (* volání, vrátí: 9 *)

Aplikace[editovat | editovat zdroj]

Pomocí zvláštní notace[editovat | editovat zdroj]

Funkci lze na vstupní parametry aplikovat různými způsoby — buď pomocí speciálních funkcí jako Apply, jak je rozebráno níže, anebo pomocí odpovídající syntaxe, jak si ukážeme v následujícím. Notací pro aplikaci nějaké funkce f na vstupní parametry existuje několik[103], viz tabulku níže:

Aplikace funkce na vstupní parametry
Druh Syntaxe Popis Příklad
Normální notace f[vstupy] vstupní parametry v hranatých závorkách, před nimiž je napsáno jméno funkce Mod[5, 2] (* vrátí: 1 *)
Prefixová notace f@vstup jméno funkce následované zavináčem a vstupním parametrem Print@"Ahoj!" (* vypíše: Ahoj! *)
Infixová notace vstup1~f~vstup2 první a druhý vstupní parametr jsou odděleny dvěma vlnovkami, mezi něž je vloženo jméno funkce {a, b}~Join~{c} (* vrátí: {a, b, c} *)
Postfixová notace vstup//f za vstupními parametry následuje dvojité lomítko a jméno funkce {{1}, {2}}//Flatten (* vrátí: {1, 2} *)

Tyto notace nejsou zcela ekvivalentní. Jednak se liší v precedenci vyhodnocování[104], jednak umožňuje prefixová a postfixová notace jen jediný vstup a infixová notace vstupy dva. V tabulce jsou notace seřazeny s klesající precedencí a tak např. f @ 23 // g vrátí g[f[23]]. Pokud jde o počet parametrů, tak lze daná omezení částečně obejít tím, že se všechny vstupní parametry vepíšou do seznamu a tento seznam se předá jako jediný parametr dané funkci, viz např. f @ {a, b, c}, které vrátí f[{a, b, c}]. Je samozřejmě nutné odpovídajícím způsobem upravit i definici funkce, má-li tato brát vstupní parametry jako prvky seznamu.

Pomocí funkcí vyšších řádů[editovat | editovat zdroj]

Aplikaci libovolné funkce na vstupní parametry lze provést i pomocí funkce Apply[105]:

Apply[f, {a, b, c}] (* vrátí: f[a, b, c] *)
f @@ {a, b, c} (* ekvivalentní kompaktní zápis *)

Funkce Apply má širší okruh použití, kdy lze s pomocí jejího druhého parametru nastavit, jak se daná funkce aplikuje na vícero vstupních hodnot umístěných do seznamů či jiných výrazů:

Apply[f, {{1, 2}, {3, 4}}, {1}] (* vrátí: {f[1, 2], f[3, 4]} *)
f @@@ {{1, 2}, {3, 4}} (* ekvivalentní kompaktní zápis *)

Podobně se chová funkce Map[65]:

Map[f, {1, 2, 3, 4}] (* vrátí: {f[1], f[2], f[3], f[4]} *)
f /@ {1, 2, 3, 4} (* ekvivalentní kompaktní zápis *)

Map[f, {{1, 2}, {3, 4}}, {2}] (* vrátí: {{f[1], f[2]}, {f[3], f[4]}} *)
Map[f, {{1, 2}, {3, 4}}] (* vrátí: {f[{1, 2}], f[{3, 4}]} *)

Aplikaci několika funkcí lze i řetězit způsobem, který reflektuje matematické skládání funkcí. Výrazem Composition[f,g] či ekvivalentně f @* g je představována funkce, která na daný vstup x vrátí f[g[x]]. Je podporována i postfixová varianta RightComposition[f,g] či ekvivalentně f /* g, která na daný vstup x vrátí g[f[x]]. Srovnej tři řádky se stejnou funkcionalitou:

f /@ (g /@ {1, 2, 3}) (* vrátí: {f[g[1]], f[g[2]], f[g[3]]} *)
f[g[#]]& /@ {1, 2, 3} (* totéž s využitím ryzí funkce *)
f @* g /@ {1, 2, 3} (* totéž s využitím skládání funkcí *)

WL nabízí řadu dalších funkcí, s jejichž pomocí lze programově aplikovat funkci na různě strukturované vstupy[106], viz např. funkce Nest a Fold v sekci „Cykly a jejich ekvivalenty“. Dalšími funkcemi jsou např. Thread a MapThread s následující funkcionalitou:

Thread[{a, b, c} -> {1, 2, 3}] (* vrátí: {a->1, b->2, c->3} *)
MapThread[f, {{a, b, c}, {1, 2, 3}}] (* vrátí: {f[a, 1], f[b, 2], f[c, 3]} *)

Ve verzi 12.2 byla zavedena funkce ApplyTo, která zobecňuje přiřazovací operátory typu *= na libovolný zadaný operátor. Předpokládejme, že do proměnné x je uložena hodnota h a na tuto proměnnou chceme aplikovat funkci f a výslednou hodnotu opět uložit do proměnné x. Toto lze provést kódem x = f[x], kde je nutno dvakrát vypsat jméno proměnné. Totéž lze provést i kódem ApplyTo[x, f] či ekvivalentně x //= f.

Volby[editovat | editovat zdroj]

Chování funkce lze ovlivnit nejen vstupy, ale i volbami (angl. options)[107], které připomínají pojmenované argumenty v Pythonu[pozn. 19]. Volby mají tvar přiřazovacích pravidel nazevVolby -> jejiHodnota[pozn. 20], přičemž jejich název může být buď symbol nebo řetězec. Konkrétní hodnotu dané volby lze vepsat jako pravidlo při volání funkce do hranatých závorek spolu s ostatními argumenty. Například nadpis grafu vytvořeného funkcí Plot lze specifikovat volbou PlotLabel:

Plot[Sin[x], {x, 0, Pi}, PlotLabel->"Graf funkce sinus"] (* nadpis grafu zní "Graf funkce sinus" *)

Hodnotu voleb lze změnit i funkcí SetOptions a to následovně:

SetOptions[Plot, PlotLabel->"Graf funkce sinus"];
Plot[Sin[x], {x, 0, Pi}] (* nadpis grafu zní "Graf funkce sinus" *)

Tento druhý způsob je vhodnější například ve chvílích, kdy je třeba měnit volbu u několikera volání téže funkce.

Volby lze dodat i do uživatelem definovaných funkcí. Nejprve je třeba výrazem Options určit, jaké volby má daná funkce podporovat. Do definice funkce je pak třeba vložit vzor OptionsPattern[][pozn. 21] a v těle funkce pak funkcí OptionValue získat hodnotu dané volby[109]. Jednoduchá funkce pak může vypadat následovně:

Options[f] = {"MojeVolba"->True}; (* definuj volby *)
f[x_, OptionsPattern[]] := Module[{v}, (* do seznamu parametrů je vložen vzor OptionsPattern[] *)
    v = OptionValue["MojeVolba"]; (* do proměnné v vlož hodnotu volby "MojeVolba" *)
    If[v, x, x^2]
];
f[3, "MojeVolba"->False] (* volání funkce, vrátí: 9 *)

Atributy[editovat | editovat zdroj]

Každá funkce ve WL se může vyznačovat i jedním či více atributy (angl. attributes), jež specifikují obecné chování funkce[110][pozn. 22]. Seznam všech atributů dané funkce f lze održet voláním Attributes[f]. Atribut nový lze nastavit funkcí SetAttributes a stávající atribut lze smazat funkcí ClearAttributes. Například funkce Sin, představující sinus, má ve verzi 13.1.0 atributy {Listable, NumericFunction, Protected}. Atribut Listable značí, že se má při aplikaci na seznam tato funkce aplikovat automaticky na každý člen seznamu zvlášť. Atribut NumericFunction říká, že funkce na číselné vstupy vrátí číselnou hodnotu a konečně atribut Protected značí, že funkci Sin nelze přímo předefinovat[pozn. 23]. Roli atributu Listable lze snadno ilustrovat na následujícím příkladu, kde je tento atribut přiřazen symbolu g:

SetAttributes[g, Listable]; (* symbolu g je nastaven atribut Listable *)
g[{1, 2, 3}] (* vrátí: {g[1], g[2], g[3]} *)
ClearAttributes[g, Listable]; (* atribut Listable je smazán *)
g[{1, 2, 3}] (* vrátí: g[{1, 2, 3}] *)

Všimněme si, že jsme výše ani žádnou definici symbolu g nepřiřadili. Uvedené chování je určeno čistě atributem.

Atributů existuje celá řada[111]. Například atribut HoldAll říká, že se vstupní argumenty nemají před voláním funkce vyhodnotit. Standardně se například výraz f[1+1] nejprve vyhodnotí jako f[2] a teprve tehdy je volána funkce f. Pokud má f ale atribut HoldAll, je do f přímo zaslán výraz 1+1, jenž je interně interpretován jako Plus[1,1] a lze na něm provádět v těle funkce dodatečné operace.

Chybová a dokumentační hlášení[editovat | editovat zdroj]

Pro danou funkci f lze specifikovat text chybových hlášení syntaxí f::jmeno = "text", kde jmeno je jméno chybové hlášky a "text" je její znění[112]. Danou hlášku lze v těle funkce vyvolat funkcí Message[113]. Srovnej

f::nedelnulou = "Dělení nulou!";
f[x_, y_] := If[y == 0, Message[f::nedelnulou], x/y]

Při volání funkce f[x, 0] vypíše tato text "Dělení nulou!". Chybové hlášení může obsahovat i parametry, které se vkládají do řetězce stylem používaným funkcí StringForm:

f::spatnyvstup = "Špatný vstup: ``";
f[x_] := If[x != 0, Message[f::spatnyvstup, x], x]

Při volání f[32] vypíše funkce hlášení "Špatný vstup: 32".

Zvláštní postavení má hlášení s vyhrazeným názvem usage[6][114], které místo chybového hlášení představuje dokumentační řetězec, který se vypíše při vyvolání nápovědy pro danou funkci:

f::usage = "Zbytečná funkce";
f[x_] := 1
?f (* vypíše "Zbytečná funkce" *)

Pokročilé definice[editovat | editovat zdroj]

Při volání funkce může dát editor uživateli na srozuměnou, zda je do volání třeba doplnit parametry. Například v případě, kdy uživatel napíše do volání funkce parametry dva a je přitom povolen jen jeden, je druhý parametr zvýrazněn červeně. Informaci tohoto rázu lze k definované funkci přiřadit pomocí výrazu SyntaxInformation. V sekci „Pokročilá definice funkce“ článku Wolfram Language lze nalézt příklad definice funkce využívající tuto a další pokročilé možnosti probrané výše.

Ve WL jsou funkce interně reprezentovány jako nahrazovací pravidla v seznamech, které lze vyvolat funkcemi UpValues, DownValues, OwnValues či SubValues[115][48][116]. Tyto funkce lze aplikovat na kterýkoliv symbol ve WL, ne jen na funkce. Seznam vrácený funkcí OwnValues obsahuje pravidla vyplývající z přiřazení nějaké hodnoty danému symbolu:

a = 3;
OwnValues[a] (* vrátí: {HoldPattern[a]:>3} *)

kde hlavička HoldPattern zajišťuje, že se výraz a automaticky nevyhodnotí na hodnotu 3. Podobně seznam DownValues obsahuje pravidla, jež vyplývají z přiřazení ve tvaru f[var_] := telo typické pro funkce:

f[x_] := x^2
DownValues[f] (* vrátí: {HoldPattern[f[x_]]:>x^2 *)

Funkce lze ale definovat i se dvěma a více posloupnostmi argumentů, kde je každý uzavřen mezi hranaté závorky. Takováto přiřazení jsou uchovávána v seznamu vyvolaným funkcí Subvalues:

f[x_][y_] := x^y
SubValues[f] (* vrátí: {HoldPattern[f[x_][y_]]:>x^y *)

Tím se dostáváme k poslednímu seznamu přiřazení spravovaného funkcí UpValues[117]. Tato přiřazení odpovídají definicím, kdy namísto specifikování toho, jak má daná funkce působit na vstupní hodnoty, určíme pro konkrétní hodnotu, jak na ní má působit daná funkce. Uvažme situaci, kdy definujeme novou symbolickou konstantu konst a chceme, aby funkce sinus měla pro tuto konstatu hodnotu , to jest Sin[konst] = 0.2, aniž bychom třeba konstantě samotné přiřadili jakoukoli hodnotu. Buď můžeme zasáhnout do definice předdefinované funkce Sin a uměle do ní vložit přiřazení Sin[konst] = 0.2, anebo můžeme toto přiřazení vložit do definice konstanty konst, čímž nedojde k jakékoliv manipulaci s definicí funkce Sin. Tento druhý způsob odpovídá přiřazení ve smyslu UpValues. Tato přiřazení mají speciální syntaxi, kde rozdíly mezi všemi čtyřmi způsoby níže leží za rámcem tohoto článku:

a/:f[a] = hod (* definice pomocí TagSet *)
a/:f[a] := hod (* definice pomocí TagSetDelayed *)
f[a] ^= hod (* definice pomocí UpSet *)
f[a] ^:= hod (* definice pomocí UpSetDelayed *)

Výše uvedený příklad by tak šlo definovat způsobem konst/:Sin[konst] = 0.2.

Ostatní[editovat | editovat zdroj]

V následujícím je neúplný výčet některých dalších sad funkcí seskupených podle jejich funkcionality.

Externí soubory[editovat | editovat zdroj]

Data lze získat funkcí Import, exportovat pak funkcí Export[118]. Uložit definici nějaké proměnné, funkce či datové struktury lze funkcí Save, jež vytvoří externí textový soubor, nebo funkcí DumpSave, jež vytvoří externí binární soubor. Získat kód z externího souboru lze funkcí Get (zkráceně <<), uložit data či kód do externího souboru lze funkcí Put (>>) či PutAppend (>>>), která původní obsah nepřepisuje a jen přidává další obsah na konec souboru[119].

data = Import["staradata.txt"]; (* importuj data ze souboru "staradata.txt" *)
data >> "novadata.txt" (* zapiš hodnotu proměnné data do souboru "novadata.txt" *)

Úprava výrazů[editovat | editovat zdroj]

Podporováno je mnoho funkcí pro algebraické a další úpravy symbolických výrazů[120][121]. Zjednodušit daný výraz lze funkcí Simplify, která aplikuje na vstupní výraz různá transformační pravidla ve snaze tento výraz zjednodušit. Větším počtem transformačních pravidel disponuje příbuzná funkce FullSimplify. Je-li důležité při zjednodušení uvést i všechny podmínky, za kterých lze vstupní výraz zjednodušit, je vhodnější použít funkci Reduce. Řešení rovnic a jejich soustav lze funkcí Solve, logické výrazy lze zjednodušovat pomocí funkce Resolve apod.

Simplify[Sin[x]^2 + Cos[x]^2] (* vrátí: 1 *)
Solve[x^2 + 3x + 2 == 0] (* vrátí: {{x->-2}, {x->-1}} *)
Reduce[x^2 + 3x + 2 == 0] (* vrátí: x == -2 || x == -1 *)

Regulární výrazy[editovat | editovat zdroj]

WL umožňuje zadávat regulární výrazy dvěma způsoby. Buď lze do funkce RegularExpression vepsat řetězec ve stylu jazyka Perl, který odpovídá danému regulárnímu výrazu, anebo lze použít řetězcové vzory (angl. string patterns), které jsou řetězcovou obdobou WL vzorů[27]. Řetězcové vzory jsou výrazy s hlavičkou StringExpression, které mají syntaxi velmi podobnou vzorům s hlavním rozdílem, že jednotlivé části vzoru jsou pospojovány dvojitými vlnovkami ~~ a jsou podporovány primitivy specifické pro řetězce[22]. Například vzor "t"~~_~~"k" představuje řetězce o třech znacích, jejichž první znak je "t" a poslední znak je "k". Takovému vzoru vyhovují například slova tak, tik, tok, tuk.

StringMatchQ["tak", "t"~~_~~"k"] (* vrátí: True *)
StringMatchQ["taak", "t"~~_~~"k"] (* vrátí: False *)

Paralelizované výpočty[editovat | editovat zdroj]

Paralelizace je umožněna funkcemi jako Parallelize, ParallelTable či ParallelDo[122]. Tímto způsobem lze buď distribuovat výpočet mezi několik výpočetních jader na jednom počítači, anebo lze výpočet poslat do výpočetních clusterů. Výpočetní jádra se nastartují a inicializují automaticky při prvním volání funkce jako ParallelTable. Totéž lze ale udělat i manuálně funkcemi LaunchKernels a DistributeDefinitions. Od verze 12.2 lze odeslat kód do vzdáleného WL výpočetního jádra pomocí funkce RemoteEvaluate či nechat výpočet provádět na vzdálených serverech spravovaných třetími stranami pomocí funkcí jako RemoteBatchSubmit[123].

Grafika[editovat | editovat zdroj]

Související informace naleznete také v článku Mathematica#Tvorba grafiky.

WL dovoluje vytvářet dvourozměrnou rastrovou (výraz Image) i vektorovou (výraz Graphics) grafiku a jejich trojrozměrné obdoby (Image3D a Graphics3D)[124]. Je podporována sada grafických primitiv, s nimiž lze programově vytvářet vektorovou grafiku[125]. Pro dvourozměrnou vektorovou grafiku lze tuto kreslit přímo v editoru i manuálně, přičemž od verze 12.2 je tato funkcionalita zabalena do prostředí Canvas[pozn. 24]. Spolu s tím lze vykreslovat grafy funkcí jak ve dvou tak třech rozměrech. Základními funkcemi jsou Plot pro vykreslení grafu reálné funkce jedné proměnné a Plot3D pro vykreslení reálné funkce dvou proměnných.

Plot[Sin[x], {x, 0, 2 Pi}] (* vykreslí sinusoidu v intervalu [0, Pi] *)
Graphics[{Blue, Rectangle[{0, 0}, {2, 1}]}] (* vykreslí modrý obdélník mezi body {0, 0} a {2, 1} *)

Dynamické výrazy[editovat | editovat zdroj]

Související informace naleznete také v článku Mathematica#Interakce.

WL podporuje tvorbu dynamicky se měnících výrazů, čímž lze přímo v editoru vytvářet interaktivní grafická uživatelská prostředí[126]. Vysokoúrovňovou funkcí pro tvorbu interaktivního prostředí je Manipulate, jejímž prvním parametrem je kód, jenž se má dynamicky obměňovat, a další parametry jsou vstupní dynamické proměnné. Pro ilustraci je níže uveden kód, který vytvoří uživatelské prostředí, v němž je vykreslována sinusoida v mezích, které jsou dynamicky nastavovány uživatelem:

Manipulate[Plot[Sin[x], {x, min, max}], {min, Pi, 2 Pi}, {max, Pi, 2 Pi}] (* vytvoří interaktivní prostředí, kde může uživatel nastavit hodnoty parametrů min a max *)
(* při každé změně parametru se dynamicky zavolá příkaz Plot a automaticky se překreslí graf sinusoidy *)

Nízkoúrovňovější variantou, disponující dodatečnou funkčností, je využití hlavičky Dynamic, kterou lze obalit výraz, jenž se má dynamicky vyhodnocovat[127]. Jako příklad uveďme následující kód:

Slider[Dynamic[x]] (* vytvoří vodorovný posuvník *)
Dynamic[x] (* zobrazí aktuální polohu posuvníku *)

který zobrazí v editoru vodorovný posuvník, který lze myší posouvat, a aktuální poloha posuvníku je zobrazena jako reálné číslo pod posuvníkem. Dynamické struktury lze vnořovat a vytvářet komplexní uživatelská prostředí, často však výměnou za zvýšené výpočetní nároky a pomalejší odezvu. Hodnoty dynamických proměnných lze lokalizovat pomocí DynamicModule, čímž lze vytvářet obecnější struktury, než které jsou dostupné skrze Manipulate.

Systém udržuje interně seznam všech výrazů, které se mají dynamicky měnit, a aktualizuje jen ty, které jsou v daném okamžiku explicitně viditelné uživateli na obrazovce. Jinak je vyhodnocování pozastaveno. Aktualizace některých výrazů je prováděna přímo front endem bez nutnosti zatěžovat výpočetní jádro. Obecně komunikuje front end s jádrem třemi kanály[128] — první kanál slouží ke standardnímu vyhodnocování příkazů, druhým kanálem posílá jádro požadavky front endu a kanál třetí, preemptivní, pak slouží k synchronnímu vyhodnocování dynamických výrazů. Takto lze současně provádět výpočty a interagovat s prostředím, aniž by čekání na uživatele znemožňovalo standardní vyhodnocování příkazů z front endu. Při větší zátěži však vyhodnocování výrazů z preemptivního kanálu může zablokovat front end.

Odkazy[editovat | editovat zdroj]

Poznámky[editovat | editovat zdroj]

  1. Přísně vzato je počet posledních výstupů udržovaných v paměti omezen interním parametrem $HistoryLength, jehož výchozí hodnota je nastavena na Infinity, tedy nekonečno.
  2. Plnou dokumentaci pak lze v editoru vyvolat stisknutím klávesy F1 ve chvíli, kde se kurzor nachází kdekoli ve jméně dotyčného symbolu.
  3. Volání funkce AtomQ na takovéto konstrukty vrátí True. Viz též oddíl "Vše je výraz" v článku Wolfram Language.
  4. Přiřazení hodnoty do proměnné lze zamezit buď použitím funkce Protect či použitím formálních proměnných vkládaných zápisy \[FormalA], \[FormalB] atd.
  5. Jsou-li k danému symbolu přiřazeny například dodatečné volby či atributy, jsou tyto při volání funkce Clear ponechány. Pro smazání jak hodnot, tak těchto dodatečných metadat, lze použít funkci ClearAll.
  6. U objektů, které nelze přímo vyjádřit v textové podobě, se použije zástupný řetězec. Například volání funkce ToString an obrázek s hlavičkou Image vrátí řetězec "-Image-".
  7. Hlavička struktury zůstává stále stejná a sice List, označení PackedArray je platné pouze pro vnitřní implementaci.
  8. Konkrétní navrácené hodnoty jsou mohou lišit od níže vypsaných.
  9. Toto chování může vést k neočekávanému chování uvnitř funkcí, když se středník zapomene napsat. Kód na řádku nezakončeném středníkem je totiž vynásoben s kódem na řádku následujícím a výsledný výraz je vyhodnocen. Namísto toho, aby byly oba řádky vyhodnoceny zvlášť jeden po druhém.
  10. Konkrétní číselné hodnoty se mohou v daném běhu programu lišit. Pro inicializaci generátoru náhodných čísel lze použít příkaz SeedRandom.
  11. Poznamenejme, že vykřičník musí stát před negovaným výrazem. Pokud stojí za ním (a!), je vykřičník interpretován jako faktoriál. Pro zajímavost dodejme, že dva vykřičníky za výrazem (a!!) označují dvojitý faktoriál.
  12. Některé funkce vrací kromě tohoto výrazu při neúspěchu i obdobný výraz Success při úspěšném proběhnutí.
  13. Jméno vznikne připojením znaku dolaru $ ke jménu proměnné, za který je dále vloženo číslo, které je pro daný běh jádra jedinečné a je uloženo do interní proměnné $ModuleNumber, jež se při každém volání inkrementuje. Lokální proměnné v Module navíc dostávají dodatečný atribut Temporary[86].
  14. Pokud je tento řádek ukončen středníkem, je návratovou hodnotou symbol Null.
  15. Takto definovaná funkce sinc je spojitá ve všech bodech. Také podotkněme, že ve WL existuje předdefinovaná funkce Sinc.
  16. Toto chování se obecně označuje jako uzávěr či anglicky closure.
  17. Výraz #0 označuje funkci samotnou, což lze využít např. při rekurzi.
  18. Tento zápis lze použít od verze 12.2, ačkoli již v předchozích verzích lze tohoto způsobu použít, pokud se místo |-> rovnou použije znak \[Function].
  19. Na rozdíl od Pythonu ale nemusejí mimo jiné stát až na konci seznamu argumentů a nelze též tentýž parametr jednou volat jako poziční a jindy jako pojmenovaný.
  20. Ve výjimečných případech je nutno použít odložené nahrazení nazevVolby :> jejiHodnota.
  21. Do verze 6 se místo OptionsPattern[] používal vzor ve stylu opts___?OptionQ a místo OptionValue bylo nutno psát kód ve stylu volba /. {opts} /. Options[funkce][108].
  22. Atributy ve WL nemají nic společného s datovými položkami, které se též nazývají atributy, známými z objektově orientovaného programování.
  23. Atribut Protected lze odstranit funkcí Unprotect a definici funkce lze pak změnit.
  24. V dřívějších verzích lze v editoru vyvolat dialogové okno s kreslicími nástroji.

Reference[editovat | editovat zdroj]

  1. Some General Notations and Conventions—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  2. Forms of Input and Output—Textual Input and Output—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-28]. Dostupné online. 
  3. Use the Full Range of Unicode Characters: New in Wolfram Language 12. www.wolfram.com [online]. [cit. 2022-09-20]. Dostupné online. (anglicky) 
  4. Mathematical and Other Notation—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-09-18]. Dostupné online. 
  5. a b Input Syntax—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-09-18]. Dostupné online. 
  6. a b c Documentation Constructs—Textual Input and Output—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  7. Use Previous Outputs in a Computation—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  8. Information—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  9. Find All Defined Functions—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  10. Everything Is an Expression—Expressions—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-28]. Dostupné online. 
  11. CompoundExpression—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-28]. Dostupné online. 
  12. Symbol—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  13. 3. An Informal Introduction to Python — Python 3.10.7 documentation. docs.python.org [online]. [cit. 2022-09-26]. Dostupné online. 
  14. Clear Definitions for Symbols and Functions—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  15. Types of Numbers—Numbers—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-28]. Dostupné online. 
  16. Digits in Numbers—Numbers—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-28]. Dostupné online. 
  17. Numerical Precision—Numbers—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-28]. Dostupné online. 
  18. Arbitrary‐Precision Numbers—Numbers—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-28]. Dostupné online. 
  19. Indeterminate and Infinite Results—Numbers—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-28]. Dostupné online. 
  20. Machine‐Precision Numbers—Numbers—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-28]. Dostupné online. 
  21. Mathematical Constants—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-28]. Dostupné online. 
  22. a b Strings and Characters—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-28]. Dostupné online. 
  23. String Manipulation—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-28]. Dostupné online. 
  24. Converting between Strings, Boxes, and Expressions—Textual Input and Output—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-28]. Dostupné online. 
  25. Working with Templates—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-28]. Dostupné online. 
  26. String Representation of Boxes—Textual Input and Output—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-28]. Dostupné online. 
  27. a b Working with String Patterns—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-28]. Dostupné online. 
  28. Data Structures—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  29. Nested Lists—Manipulating Lists—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  30. List ({...})—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  31. Manipulating Elements of Lists—Manipulating Lists—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  32. Adding, Removing, and Modifying List Elements—Lists—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  33. list manipulation - What is a Mathematica packed array?. Mathematica Stack Exchange [online]. [cit. 2022-10-27]. Dostupné online. (anglicky) 
  34. PackedArrayQ—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  35. Linear Algebra—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  36. Associations and immutability - Online Technical Discussion Groups—Wolfram Community. community.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. (anglicky) 
  37. version 10 - How to make use of Associations?. Mathematica Stack Exchange [online]. [cit. 2022-10-27]. Dostupné online. (anglicky) 
  38. Association (<|...|>)—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  39. a b Associations—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  40. Part ([[...]])—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  41. a b c Function (&,|->)—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  42. Making Definitions for Indexed Objects—Transformation Rules and Definitions—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  43. Arithmetic Functions—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  44. Arithmetic—Numerical Operations on Functions—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  45. NonCommutativeMultiply (**)—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  46. Immediate and Delayed Definitions—Transformation Rules and Definitions—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  47. Special Forms of Assignment—Transformation Rules and Definitions—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  48. a b Assignments—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  49. Relational and Logical Operators—Manipulating Equations and Inequalities—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  50. SameQ (===)—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  51. Testing Expressions—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  52. Logic & Boolean Algebra—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  53. Bitwise Operations—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  54. Quantifiers—Manipulating Equations and Inequalities—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  55. Conditionals—Evaluation of Expressions—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  56. If—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  57. Switch—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  58. Which—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  59. Looping Constructs—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  60. For—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  61. core language - Why should I avoid the For loop in Mathematica?. Mathematica Stack Exchange [online]. [cit. 2022-10-27]. Dostupné online. (anglicky) 
  62. performance tuning - Alternatives to procedural loops and iterating over lists in Mathematica. Mathematica Stack Exchange [online]. [cit. 2022-10-27]. Dostupné online. (anglicky) 
  63. Repetitive Operations—Functions and Programs—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  64. Making Tables of Values—Lists—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  65. a b Map (/@)—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  66. Applying Functions Repeatedly—Functional Operations—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  67. Flow Control—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  68. Messages—Textual Input and Output—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  69. Print Intermediate Values of a Variable—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  70. Tuning & Debugging—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  71. Robustness & Error Handling—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-27]. Dostupné online. 
  72. Patterns—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  73. Blank—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  74. Specifying Types of Expression in Patterns—Patterns—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  75. Naming Pieces of Patterns—Patterns—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  76. Putting Constraints on Patterns—Patterns—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  77. Pattern Matching Functions—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  78. Rules—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  79. Transformation Rules—Patterns and Transformation Rules—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  80. Applying Transformation Rules—Transformation Rules and Definitions—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  81. Scoping Constructs—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-09-18]. Dostupné online. 
  82. a b What are the use cases for different scoping constructs?. Mathematica Stack Exchange [online]. [cit. 2022-09-18]. Dostupné online. (anglicky) 
  83. Blocks and Local Values—Modularity and the Naming of Things—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  84. Modules and Local Variables—Modularity and the Naming of Things—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  85. Blocks Compared with Modules—Modularity and the Naming of Things—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  86. Temporary—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  87. Local Constants—Modularity and the Naming of Things—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  88. Substitute Values of Variables in Functions That Hold Their Arguments—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  89. Contexts—Modularity and the Naming of Things—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  90. Evaluation > Notebook's Default Context—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  91. Create a Package File—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  92. Setting Up Wolfram Language Packages—Modularity and the Naming of Things—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  93. Wolfram LibraryLink User Guide—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  94. Paclets Overview—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  95. Wolfram Language Paclet Repository. resources.wolframcloud.com [online]. [cit. 2022-10-26]. Dostupné online. 
  96. Notes for Programming Language Experts about Wolfram Language. www.wolfram.com [online]. [cit. 2022-09-21]. Dostupné online. (anglicky) 
  97. a b Patterns for Some Common Types of Expression—Patterns—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  98. Optional and Default Arguments—Patterns—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  99. Making Definitions for Functions—Transformation Rules and Definitions—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  100. The Ordering of Definitions—Transformation Rules and Definitions—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  101. Functions That Remember Values They Have Found—Transformation Rules and Definitions—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  102. a b Pure Functions—Functional Operations—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  103. Special Ways to Input Expressions—Expressions—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  104. Operator Input Forms—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-25]. Dostupné online. 
  105. Apply (@@)—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  106. Functional Operations—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  107. Manipulating Options—Functions and Programs—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  108. wolfram mathematica - What are the benefits of switching from Rule and /. to OptionsPattern[] and OptionValue in a large application?. Stack Overflow [online]. [cit. 2022-10-25]. Dostupné online. (anglicky) 
  109. Options Management—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-25]. Dostupné online. 
  110. Attributes—Evaluation of Expressions—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  111. Attributes—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-25]. Dostupné online. 
  112. Set Up Error Checking and Messages in a Function—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-25]. Dostupné online. 
  113. Messages—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-25]. Dostupné online. 
  114. MessageName (::)—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-25]. Dostupné online. 
  115. Associating Definitions with Different Symbols—Transformation Rules and Definitions—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  116. assignment - What is the distinction between DownValues, UpValues, SubValues, and OwnValues?. Mathematica Stack Exchange [online]. [cit. 2022-10-26]. Dostupné online. (anglicky) 
  117. UpValues—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  118. Importing and Exporting—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  119. Files, Streams, and External Operations—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  120. Algebraic Manipulation—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  121. Algebraic Calculations—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  122. Parallel Computing Tools User Guide—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-20]. Dostupné online. 
  123. Remote Batch Jobs—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  124. Graphics and Sound—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  125. The Structure of Graphics and Sound—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  126. Custom Interface Construction—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-20]. Dostupné online. 
  127. Introduction to Dynamic—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-10-26]. Dostupné online. 
  128. Advanced Dynamic Functionality—Wolfram Language Documentation. reference.wolfram.com [online]. [cit. 2022-09-11]. Dostupné online. 

Související články[editovat | editovat zdroj]