hledání pokladu v bludišti
- zkouším postupně všechny cesty
- bludiště obecně není strom (procházím typicky nějaký spojitý graf)
- může vzniknout situace, že dojdu na křižovatku, na které už jsem byl
- název algoritmu
- prohledávání do hloubky, prohledávání s návratem
- DFS (depth-first search), backtracking
proskákání šachovnice koněm – příliš časově náročné
urychlení prohledávání do hloubky
- ořezávání – v průběhu vyhodnocuji, jestli má smysl postupovat ve stromu dál
- osm dam na šachovnici (aby se dvě navzájem neohrožovaly)
- bez ořezávání – zkoušet všechny výběry 8 polí z 64
- základní ořezávání – na každém řádku právě jedna dáma, po umístění všech osmi dam otestovat kolize
- lepší ořezávání – hned při umišťování každé dámy testovat kolize s dámami umístěnými na předchozích řádcích
- magické čtverce
- heuristika – odhad, kde je asi větší šance na nalezení řešení (u úloh, kde hledám jedno řešení) → podle toho určím pořadí procházení variant možných pokračování
- u koně volím ty umístění, z nichž mám nejmenší počet možných dalších kroků
prohledávání stavového prostoru do šířky – breadth-first search (BFS), algoritmus „vlny“
- souběžně zkoušíme všechny možné varianty pokračování výpočtu až do nalezení řešení úlohy – v každé vrstvě zkoušíme všechny možnosti zleva doprava
- může být paměťově velmi náročné, až nepoužitelné
- vždy najde nejkratší možné řešení co do počtu kroků
- k nalezení samotné cesty je potřeba „zpětný chod“
zkouška
- ve zkouškovém období
- informace na moodlu, ukázka úloh z minulého ročníku
- velká písemka každý týden ve zkouškovém v pondělí dopoledne, termíny společné pro obě paralelky v N1
- potřebujeme zápočet
- termíny budou vypsány kolem Vánoc
- povinná písemná a nepovinná ústní část
- v písemné části asi 4 příklady
- úlohy vyřešíme, součástí některých úloh je i napsat funkci v Pythonu, ale není naší povinností ji odladit, nebudou se kontrolovat detaily syntaxe, jde hlavně o princip
- zkoušku budeme řešit v Moodlu, budeme moct používat vlastní notebook s Moodlem (takže můžeme používat prezentace z přednášek)
- je možná i papírová varianta
- kdo dostane 2 nebo 3 a bude si chtít zlepšit známku, bude moct přijít na ústní část zkoušky – výsledná známka se bude skládat ze dvou známek (může být lepší nebo i horší)
minimax
- na tahu bílého se hledá maximum, na tahu černého minimum
- u malých her se dá postavit celý strom
- řeší se průchodem do hloubky (klasický backtracking), v listech se výsledek ohodnotí (výhra = 1, prohra = 0, remíza = –1)
- někdy se používá negamax – prohazuje se znaménko, protože min(a,b)=−max(−a,−b)
- u velkých her rozvíjím hru do určité hloubky, pak to zaříznu (čím větší hloubka, tím chytřejší tahy)
- v té hloubce se na pozice zavolá statická ohodnocovací funkce, která každou z nich ohodnotí
- často se ohodnocení vylepšuje tak, že pokud je koncová pozice „živá“ (nastávají výrazné změny na herním poli), tak se strom počítá ještě o úroveň níž
- ořezávání stromu
- ztrátové
- provedu statické ohodnocení po několika málo vrstvách
- část nejhorších pozic odmítnu, zbytek rozvíjím dál
- bezztrátové – alfa-beta-prořezávání
- využívá principu minimaxu – jeden hráč hledá minimum, druhý maximum, tedy v některých situacích není potřeba dopočítávat další varianty hry
- dá se přidat heuristika – procházím postupně do uzlů, které mají lepší (nebo naopak horší) výsledek statického ohodnocení
rozděl a panuj (divide et impera)
- metoda rekurzivního návrhu algoritmu (programu)
- problém se rozdělí na dva podproblémy, které se obvykle řeší lépe, z jejich řešení se dá sestavit řešení původního problému
- je problematické použít tuto metodu u úloh, kdy jednotlivé podúlohy jsou na sobě závislé (mají společné části) – viz Fibonacci
- vyhodnocení aritmetického výrazu
- hanojské věže
- abych přenesl celou věž z A na B, musím nejdřív dostat horní část na C, potom přesunout spodní kotouč z A na B a pak na něj přenést horní část
- mergesort
- rozdělujeme na půl
- sléváme
- quicksort
- vyberu číslo (pivot) – typicky náhodně nebo uprostřed pole
- prvky rozdělím na menší, rovné a větší než pivot
- dá se třídit na místě – jdu zleva a zprava, hledám větší/menší, až najdu, tak prohodím a jedu dál
- v průměru počítá nejrychleji ze všech algoritmů – O(N log N)
- v nejhorším případě kvadratický (když volím špatné pivoty)
- pokud chci garantovanou složitost, tak quicksort není dobrá volba
- volba pivota
- jeden náhodně vybraný prvek
- vzorkování – medián ze tří náhodně zvolených prvků
- náhodný výběr + ověření, zda je alespoň 1/4 prvků menších a 1/4 prvků větších
- nalezení mediánu tříděného úseku (existuje algoritmus, který hledá v lineárním čase) – zajistí složitost O(N log N), ale v průměru bude pomalejší, protože vzroste multiplikativní konstanta
nalezení K-tého nejmenšího prvku z N čísel
- speciální případ – medián
- způsoby
- setřídit čísla v poli – spousta zbytečné práce
- modifikace heapsortu – K-krát odeberu minimum
- akademická hříčka: postavit v poli haldu z prvních N–K+2 prvků
- modifikace quicksortu – quickselect
- lineární algoritmus
quickselect
- po rozdělení seznamu podle pivota pracujeme dál jen s tou částí, ve které je hledaný prvek (poznáme ji podle délky – známe délky jednotlivých částí)
- v průměru má lineární složitost, v nejhorším případě kvadratickou
lineární algoritmus
- seznam rozdělím po pěti prvcích
- z každé pětice vezmu medián (práce n)
- z nalezených mediánů najdu medián (práce n/5)
- ten zvolím jako pivot
- v nejhorším případě bude v menší části 3/10 n prvků
- tento algoritmus nemusíme umět
vyhodnocení aritmetického výrazu reprezentovaného binárním stromem
- průchod preorder → prefix
- průchod inorder → infix (bez závorek)
- průchod postorder → postfix
- vyhodnocení postfixu – pomocí zásobníku (vytáhnu dvě čísla ze zásobníku, provedu operaci, výsledek vrátím do zásobníku)
- vyhodnocení výrazu v prefixové notaci
- průchod odzadu a zpracování jako u postfixu
- průchod zepředu a ukládání operací do zásobníku – při přidávání čísla do zásobníku kontrola, zda je na vrcholu zásobníku číslo, pokud ano, tak ho vyzvednu a rovnou taky operaci pod ním, tu provedu
- rekurze
převod infix → postfix – pomocí zásobníku během jednoho průchodu