TGH01 - Algoritmizace Jan Březina Technical University of Liberec 31. března 2015
Metainformace materiály: jan.brezina.matfyz.cz/vyuka/tgh (./materialy/crls8.pdf - Introduction to algorithms) SPOX: tgh.spox.spoj.pl seminární práce, pro konkrétní úlohu: formulace úlohy jako grafového problému aplikace algoritmu z přednášky na jeho řešení implementace algoritmu možná spolupráce (je třeba deklarovat) při zkoušce umět vysvětlit zkouška písemná + ústní
Záleží na kritériu: Který algoritmus je lepší?
Který algoritmus je lepší? Záleží na kritériu: Rychlost výpočtu (časová složitost)
Který algoritmus je lepší? Záleží na kritériu: Rychlost výpočtu (časová složitost) Pamět ová náročnost (pamět ová složitost)
Který algoritmus je lepší? Záleží na kritériu: Rychlost výpočtu (časová složitost) Pamět ová náročnost (pamět ová složitost) Složitost implementace (rychlost implementace)
Složitost algoritmu jako funkce vstupu Maximální zjednodušení: vstup má velikost n (něčeho) výpočet trvá T (n) elementárních kroků a potřebuje M(n) jednotek paměti
Porovnání různých složitostí Pro seriový počítač s frekvencí 1GHz (10 9 operací za sekundu) n = 10 100 1000 1000000 za 1 hodinu log n 3.3ns 6.7ns 10ns 20ns n 3.2ns 10ns 32ns 1µs 10 25 (1000x world) n 10ns 100ns 1µs 1ms 10 12 (TB) n log n 33ns 664ns 10µs 20ms 10 11 n 2 100ns 10µs 1 ms 17min 10 6 (MB) n 3 1µs 1ms 1s 31let 15000 2 n 1µs 41 n! 3ms 15 Závěr: Na konstantě nezáleží.
Asymptotická časová složitost Necht g a f jsou dvě reálné funkce reálné proměnné. g(n) = O(f(n)) pokud existuje konstanta C, že pro dost velká n je g(n) < Cf(n) g(n) = Ω(f(n)) pokud existuje konstanta c, že pro dost velká n je g(n) > cf(n) g(n) = Θ(f(n)) pokud platí g(n) = O(f(n)) i g(n) = Ω(f(n)) Přesnější notace: (g je asymptoticky menší než f) g O(f(n)) nebo také g f
Vlastnosti asymptotické složitosti Počítání, pro f i O(g i (n)): f 1 f 2 = O(g 1 g 2 ) f 1 + f 2 = O(g 1 + g 2 ) = O(max(g 1, g 2 )) f(h(n)) = O(g(h(n))) i h(f(n)) = O(h(g(n))) f(n) f(n) = O(g(n)) lim n g(n) < Nezávisí na rychlosti počítače (ukrytá v konstantě). Nezávisí na kvalitě překladače, zručnosti programátora. Pomíjí členy nižšího řádu. Platí pouze pro dost veliká data.
Příklady: analogie T f, př: n 2 + log(n) = O(n 2 ), = O(n 3 ), O(n log(n)) analogie T f, př: n 2 + log(n) = Θ(n 2 ), Ω(n 3 ), Ω(n log(n))
Příklad binární vs. Finonačiho halda Složitost operací používaných v Dijkstrově algoritmu Binární halda Fibonacci halda Vložení O(lgn) O(1) Odeber Min. O(lgn) O(lgn) Zmenšení Kĺıče O(lgn) O(1) Praxe, Boost C++ library: Generating graph...10 000 vertices, 20 000 000 edges. Running Dijkstra s with binary heap...1.46 seconds. Running Dijkstra s with Fibonacci heap...1.31 seconds. Speedup = 1.1145.
Složitost v nejhorším případě function InsertSort (A[1:n]) for i = 2... len(a) do key = A[i] j = i-1 while j > 0 and A[j] > key do A[j+1] = A[j] j = j - 1 A[j+1] = key
Dolní odhad složitosti třídění Rozhodovací strom: Počet uspořádání - listů je n! Výška stromu: log n! = log n + log(n 1) +... log 2 + log 1 n/2 log(n/2) cn log(n)
... quicksort Složitost v průměrném případě
.. dynamické pole (std::vector) Amortizovaná složitost
Složitost rekurzivních algoritmů function Rekurze (A[1:n]) Θ(n); Rekurze (A[1:n/2]); Rekurze (A[n/2:n]) T (n) = 2T (n/2) + Θ(n), T (1) = 1 Theorem (Master theorem) Pokud T (n) = at (n/b) + f(n), a 1, b > 1 1. f(n) = O(n log b a ε ), pak T (n) = Θ(n log b a ) 2. f(n) = Θ(n log b a), pak T (n) = Θ(n log b a lg(n)) 3. f(n) = Ω(n log b +ε ), pak T (n) = Θ(f(n)) Složitost Rekurze je tedy případ 2, Θ(nlgn).
Důkaz správnosti algoritmu Invariant: Vlastnost dat, která: platí na počátku (po inicializaci) zachovává se její platnost na konci implikuje splnění úkolu
Insert sort function InsertSort (A[1:n]) for i = 2... len(a) do key = A[i] j = i-1 while j > 0 and A[j] > key do A[j+1] = A[j] j = j - 1 A[j+1] = key
Správnost insert sortu Invariant: Na začátku for cyklu obsahuje A[1... i 1] prvních i 1 prvků původního pole, setříděných. Inicialiazace: První prvek původního pole tvoří setříděnou posloupnost délky 1. Zachování: Do cyklu vstupuje setříděná posloupnost prvků A[1... i 1]. Z cyklu vystupuje setříděná posloupnost prvků A[1... i]. Ukončení: For cyklus skončí pro i = n + 1, pole A[1... n] obsahuje setříděnou poslouponst prvků celého původního pole.
Pseudokód Bloky FOR, IF, WHILE vyznačeny odsazením a vertikální čarou. Hodnota čítače ve FOR má první neplatnou hodnotu po konci cyklu. // Komentář Přiřazení - porovnání -= Přístup k prvkům pole: A[i] Sekvence: 1..4, A[1..4] Atributy objektů: A.size, Child.parent Předávání parametrů funkcí hodnotou. Zkrácené vyhodnocování AND a OR.