Hlavní navigace

Názor k článku PostgreSQL 14: nové funkce, nástroje a interní optimalizace od Miroslav Šilhavý - Podle mě je to myšleno jinak. Potřebujete splnit nějaký...

  • Článek je starý, nové názory již nelze přidávat.
  • 21. 5. 2021 8:22

    Miroslav Šilhavý

    Podle mě je to myšleno jinak.
    Potřebujete splnit nějaký úkol - řekněme, naprogramovat web a CMS.

    Ten samý úkol můžete řešit dvěma způsoby:
    a) neumíte SQL a nerozumíte RDBMS a namastíte dotazy "nějak", případně použijete ORM
    b) umíte SQL a rozumíte svému RDBMS a dotazy a transakce vytvoříte tak, aby vyhovovaly zvolené databázi

    Porovnání dvou databází pak můžete provést různě. V případě ad a) nemusíte dělat žádné úpravy. Zde dost často vyhraje mysql nad postgresql, právě díky menší režii a datům rychle dohledatelným podle primárního klíče.

    V případě ad b) už ale můžete najít obrovské rozdíly. Troufnu si tvrdit, že i kdybyste se rozkrájel, tak s mysql nedokážete práci s daty zoptimalizovat k podstatně vyššímu výkonu. V případě postgresql naopak ano.

    Konkrétně využijete mnohonásobné joiny (10 joinů není nic, co by bylo považováno za "velký dotaz"), využijete agregáty, SQL funkce, window funkce, lateral joiny. Tedy vlastnosti, které mysql buďto umí pomalu, nebo nenabízí vůbec.

    Typický příklad z praxe: tři pracovníci, prodávající u McDonald's. Každý prodej je zaznamenán formou účtenky - ví se kdo, kdy a jaké zboží prodal. Chcete zjistit, který pracovník prodává zboží s nejvyšší marží (na cheeseburgeru víte, že vyděláváte méně, než na zmrzlině a pracovníci mají pokyn nabízet zmrzku). Chcete tu statistiku znát za poslední směnu a za posledních 10 směn. Směny jsou nepravidelné (některý den někdo nepracuje, každému začíná pracovní doba jindy). Zajímá Vás jak to, jestli nabízejí úspěšně zmrzlinu, ale i to, jestli jsou celkové výkonní (jeden může dobře prodávat zmrzlinu, ale obsluhuje pomaleji, takže ani ta zvýšená marže nevynahradí jeho pomalost).

    V mysql taková data nemáte šanci získat jinak, než že si oddělenými dotazy vytaháte jednotlivá data (kdy měl kdo posledních 10 směn - jeden je bude mít v předcházejících 10 dnech, jiný je bude mít rozložené na 20 dní). Zcela nezávisle spočítáte součty a marže pro poslední směnu a nezávisle pro 10 směn. Do databáze budete z aplikace posílat minimálně tři dotazy a mezi nimi bude aplikační logika. Na konci pomocí vnořených smyček vytisknete tabulku.

    V postgresu na to použijete jeden jediný velký dotaz. Směny si získáte subselectem, který využijete pro join. Pro součty za poslední směnu a za 10 směn využijete window funkce a agregáty. Data nakonec naformátujete do kostky. Jeden jediný dotaz, který má databáze možnost zoptimalizovat a zpracovat rychle (nemusí třikrát číst ta samá data, když ví, že je má sečíst pro poslední směnu a pro posledních 10 směn). V aplikaci vypíše data z kostky, aniž byste použil vnořené smyčky.

    [@Pavel Stěhule k článku: zrovna toto je šikovné užití grouping sets a na DISTINCT se docela teším, protože při těchto operacích fakt vznikají duplicity, které sice vznikají logicky, ale pro výstup dat nepřinášejí žádnou hodnotu]

    Právě v tom, kde jsou limity schopností databáze tkví to porovnání, která je výkonnější při správném užití.