Algoritmus je přesný návod či postup, kterým lze vyřešit daný typ úlohy. Pojem algoritmus se nejčastěji objevuje při programování, kdy se jím myslí teoretický princip řešení problému (oproti přesnému zápisu v konkrétním programovacím jazyce). Obecně se ale algoritmus může objevit v jakémkoli jiném vědeckém odvětví. Jako jistý druh algoritmu se může chápat i např. kuchařský recept. Zpravidla však na algoritmy klademe určitá omezení.

Vlastnosti algoritmů V užším smyslu se slovem algoritmus označují takové postupy, které splňují některé silnější požadavky: Elementárnost Algoritmus se skládá z konečného počtu jednoduchých (elementárních) kroků. Konečnost (finitnost) Každý algoritmus musí skončit v konečném počtu kroků. Tento počet kroků může být libovolně velký (podle rozsahu a hodnot vstupních údajů), ale pro každý jednotlivý vstup musí být konečný. Postupy, které tuto podmínku nesplňují, se mohou nazývat výpočetní metody. Speciálním příkladem nekonečné výpočetní metody je reaktivní proces, který průběžně reaguje s okolním prostředím. Někteří autoři však mezi algoritmy zahrnují i takovéto postupy. Obecnost (hromadnost, masovost, univerzálnost) Algoritmus neřeší jeden konkrétní problém (např. „jak spočítat 3×7“), ale obecnou třídu obdobných problémů (např. „jak spočítat součin dvou celých čísel“), má širokou množinu možných vstupů. Determinovanost Algoritmus je determinovaný, pokud za stejných podmínek (pro stejné vstupy) poskytuje stejný výstup. Tato vlastnost je požadována u velké části úloh; existují však úlohy, kdy je naopak vyžadována náhodnost (například simulace vrhu kostkou, míchání karet, generování hesel a šifrovacích klíčů); na standardních počítačích je dosažení náhodnosti obtížné. Pravděpodobnostní algoritmy v sobě mají zahrnutu náhodu a nemusí být determinované. DeterminismusKaždý krok algoritmu musí být jednoznačně a přesně definován; v každé situaci musí být naprosto zřejmé, co a jak se má provést, jak má provádění algoritmu pokračovat. Protože přirozené jazyky neposkytují naprostou přesnost a jednoznačnost vyjadřování, byly pro zápis algoritmů navrženy programovací jazyky, ve kterých má každý příkaz jasně definovaný význam. Vyjádření výpočetní metody v programovacím jazyce se nazývá program. Některé algoritmy jsou sice determinované, ale nejsou deterministické (například řadící algoritmus rychlé řazení s náhodnou volbou pivota). Výstup Algoritmus má alespoň jeden výstup, veličinu, která je v požadovaném vztahu k zadaným vstupům, a tím tvoří odpověď na problém, který algoritmus řeší (algoritmus vede od zpracování hodnot k výstupu)

V praxi jsou proto předmětem zájmu hlavně takové algoritmy, které jsou v nějakém smyslu kvalitní. Takové algoritmy splňují různá kritéria, měřená např. počtem kroků potřebných pro běh algoritmu, jednoduchost, efektivitu či eleganci. Problematikou efektivity algoritmů, tzn. metodami, jak z několika známých algoritmů řešících konkrétní problém vybrat ten vhodný, se zabývají odvětví informatiky nazývané algoritmická analýza a teorie složitosti.

Metody návrhu Algoritmus se navrhuje několika možnými způsoby:

Shora dolů – postup řešení rozkládáme na jednodušší operace, až dospějeme k elementárním krokům. Zdola nahoru – z elementárních kroků vytváříme prostředky, které nakonec umožní zvládnout požadovaný problém. Kombinace obou – obvyklý postup shora dolů doplníme "částečným krokem" zdola nahoru tím, že se například použijí knihovny funkcí, vyšší programovací jazyk nebo systém pro vytváření programů (CASE).

Paradigmata návrhu algoritmů

Při návrhu algoritmů se uplatňuje množství přístupů, které abstrahují od konkrétní úlohy. K nejužívanější metodám návrhu algoritmů patří:

Rozděl a panuj

Klasický případ aplikace postupu odshora dolů. Algoritmy typu rozděl a panuj dělí problém na menší podproblémy, na něž se rekurzivně aplikují (až po triviální podproblémy, které lze vyřešit přímo), po čemž se dílčí řešení vhodným způsobem sloučí.

Zpracovává se množina V složená z n údajů. Tato množina se rozdělí na k disjunktních podmnožin, které se zpracují každá zvlášť. Získané dílčí výsledky se pak spojí a odvodí se z nich řešení pro celou množinu V.

Klasickým případem je binární vyhledávání nebo řadící algoritmus rychlé řazení.

Hladový algoritmus

Velice přímočarý přístup k řešení určité třídy optimalizačních úloh.

Zpracovává se množina V složená z n údajů. Úkolem je najít podmnožinu W množiny V, která vyhovuje určitým podmínkám a přitom optimalizuje předepsanou účelovou funkci. Jakákoliv množina W, vyhovující daným podmínkám, se nazývá přípustné řešení. Přípustné řešení, pro které nabývá účelová funkce optimální hodnoty, se nazývá optimální řešení.

Hladový algoritmus se skládá z kroků, které budou procházet jednotlivé prvky z V, a v každém kroku rozhodne, zda se daný prvek hodí do optimálního řešení. Prvky V bude vybírat v pořadí určeném jistou výběrovou procedurou. Výběrová procedura bude založená na nějaké optimalizační míře – funkci, která může být odvozena od účelové funkce. V každém kroku ale musíme dostat přípustné řešení. Jakmile je učiněno takové rozhodnutí, už není dále revidováno. Příkladem je třeba hledání nejkratší cesty grafu.

Dynamické programování

Dynamické programování se používá v případech kdy lze optimální řešení složit z řešení jednodušších problémů. Protože se požadavky na řešení jednodušších podproblémů mohou mnohokrát opakovat, je nutné zvolit správné pořadí jejich řešení a výsledky si zapamatovat pro opakované použití.

Opírá se o princip optimality: Optimální posloupnost rozhodnutí má tu vlastnost, že ať je počáteční stav a rozhodnutí jakékoliv, musí být všechna následující rozhodnutí optimální vzhledem k výsledkům rozhodnutí prvního.

Typickým příkladem využití dynamického programování jsou grafové úlohy a jejich příslušné grafové algoritmy.

Použití hrubé síly

U některých úloh nezbývá než postupně probírat všechna možná řešení – tak zvaná metoda hrubé síly – vygenerují se všechny možné posloupnosti a pak se vybere ta nejlepší. V některých případech lze použít metody, které vynechávají popřípadě odkládají procházení možností, které zřejmě nejsou optimální.

Hledání s návratem (backtracking)

Hledání s návratem založené na prohledávání stavového prostoru problému. Též se nazývá metoda pokusů a oprav, metoda zpětného sledování, metoda prohledávání do hloubky.

Metodu je možné použít v případě, že řešením je vektor (x1,...,xn), jehož jednotlivé složky vybíráme z množiny Si, xi∈Si. Zpravidla je třeba najít n-tici, která optimalizuje nějakou účelovou funkci P(x1,...,xn). Mohou se ale také hledat všechny n-tice, které tuto podmínku splňují. Metoda vytváří n-tice jednu složku po druhé. Přitom používá účelovou funkci (nebo nějakou vhodnou pomocnou funkci) a pro každou nově vytvořenou složku testuje, zda by taková n-tice vůbec mohla být optimální nebo splňovat dané podmínky. Jestliže pro nějaké xi žádaný vektor (x1,...,xi) nemůže být optimální, není třeba už žádný takový vektor testovat a vezmeme další možnou hodnotu i-té složky. Pokud jsou vyčerpány všechny hodnoty i-té složky, vrátí se metoda zpět o jeden krok a zkouší další možnou hodnotu xi-1.

Příkladem je třeba problém osmi dam nebo chůze koně celou šachovnicí.

Algoritmická složitost

Je třeba poznamenat, že abstraktní kritérium konečnosti je pro praktické použití ještě příliš slabé. V praxi je třeba zajistit, aby algoritmus skončil „v rozumném“ čase. Za rozumný čas lze v praxi považovat takový čas, který nám umožní smysluplně využít výsledek.

Např. existuje jednoduchý algoritmus, který dokáže určit, zda v dané šachové pozici může hráč na tahu vynutit vítězství a zároveň dokáže určit nejlepší možný tah. Tento algoritmus se však nedá použít, protože by na svou činnost potřeboval ohromné množství času, jakkoli je toto množství konečné. Mimoto by takový algoritmus spotřeboval ohromné množství paměti, což je další praktický zřetel, který se uplatňuje při volbě algoritmu. I když průměrná počítačová paměť stále narůstá, pro některé algoritmy jí nebude nikdy dost.

Pro vyčíslení výpočetní složitosti algoritmů v závislosti na velikosti vstupních dat se používá asymptotický zápis závislosti výpočetního času na rozsahu úlohy (typicky na počtu vstupních údajů). Například O(log N) znamená, že počet kroků algoritmu závisí logaritmicky na velikosti vstupních dat. Pokud u takového algoritmu zdvojnásobíme rozsah vstupních údajů, doba výpočtu se zvýší o jednu jednotku času, pokud bude vstupních dat čtyřikrát více, doba výpočtu se prodlouží o dvě jednotky času, a tak dále. To je třeba případ nalezení jednoho prvku o určité hodnotě v seznamu prvků seřazeném podle hodnoty (např. nalezení jména v telefonním seznamu).

Druhy algoritmů Algoritmy můžeme klasifikovat různými způsoby. Mezi důležité druhy algoritmů patří:

Rekurzivní algoritmy, které využívají (volají) samy sebe.

Pravděpodobnostní algoritmus (někdy též probabilistické) provádí některá rozhodnutí náhodně či pseudonáhodně. V případě, že máme k dispozici více počítačů, můžeme úlohu mezi ně rozdělit, což nám umožní ji vyřešit rychleji; tomuto cíli se věnují paralelní algoritmy. Genetický algoritmus pracuje na základě napodobování biologických evolučních procesů, postupným „pěstováním“ nejlepších řešení pomocí mutací a křížení. V genetickém programování se tento postup aplikuje přímo na algoritmy (resp. programy), které jsou zde chápány jako možná řešení daného problému. Heuristický algoritmus si za cíl neklade nalézt přesné řešení, ale pouze nějaké vhodné přiblížení; používá se v situacích, kdy dostupné zdroje (např. čas) nepostačují na využití exaktních algoritmů (nebo pokud nejsou žádné vhodné exaktní algoritmy vůbec známy).

Přitom jeden algoritmus může patřit zároveň do více skupin; například může být zároveň rekurzivní a genetický.

Některé známé algoritmy Eratosthenovo síto Euklidův algoritmus Algoritmus de Casteljau Dijkstrův algoritmus Bellmanův–Fordův algoritmus

Etymologie Slovo algoritmus pochází ze jména významného perského matematika žijícího v první polovině 9. století (cca 780–840), kterým byl Abū ʻAbd Allāh Muhammad ibn Mūsā al-Chwārizmī () (doslova „Otec Abdulláha, Mohamed, syn Mojžíšův, pocházející z města Chwārizm (Chórézm, dnes Chiva)“; tento kraj se nachází v Uzbekistánu jižně od Aralského jezera). Tento učenec ve svém díle prakticky vytvořil systém arabských číslic a základy algebry (konkrétně metody řešení lineárních a kvadratických rovnic), jejíž název pochází přímo z titulu tohoto díla (Kitūb al-jabr waāl-muqūbala). Jeho jméno bylo do latiny převedeno jako algorismus, a původně znamenalo „provádění aritmetiky pomocí arabských číslic“; abacisté počítali pomocí abaku, algoristé pomocí algorismů.

Postupem času se kvůli neznalosti původu slova jeho podoba měnila, záměnou arabského kořene s kořenem řeckého slova αριθμός (arithmos) se z algorismu stal algorithmus. (Později bylo v některých jazycích včetně češtiny th změněno na t, v katalánštině se vrátilo s.) Toto slovo se používalo jako označení různých matematických postupů, např. v 18. století označoval latinský termín algorithmus infinitesimalis „metodu výpočtů s využitím nekonečně malých veličin, vynalezenou německým matematikem Leibnizem“. Slovo algoritmus v dnešním významu se používá až zhruba od 20. století.

Historie: Vývoj pojmu „algoritmus“

Starověké Řecko Algoritmy byly použity ve starověkém Řecku. Například Eratosthenovo síto nebo Eukleidův algoritmus.

Původ Slovo algoritmus pochází z 9. století a je odvozeno z příjmení perského matematika Al-Chorezmí. Slovo původně odkazovalo na pravidla provádění aritmetických operací s arabskými číslicemi, ale vyvinulo se prostřednictvím překladu matematikova jména na „algoritmus“ v 18. století a zahrnuje všechny určité postupy pro řešení problémů nebo plnění úkolů.

Diskrétní a rozeznatelné symboly