V tomto kurzu se budeme zabývat funkcionálním programovacím jazykem Haskell, se kterým jste měli možnost pracovat již v předmětu IB015 (Úvod do funkcionálního programování).
Nejdůležitější body historie Haskellu:
My budeme pracovat s překladačem GHC (The Glorious Glasgow Haskell Compilation System) a jeho interaktivní variantou GHCi. Ten podporuje rozšíření definovaná Haskellem' a je považován za průmyslový standard.
Tři základní příkazy:
ghc — překladač (vygeneruje spustitelný program);ghci — interpret (pracuje se s ním podobně jako s Hugsem, který se používal v úvodním předmětu);runhaskell — jednorázové spuštění zdrojového kódu (lze využít pro psaní skriptů).Vstupem překladače je zdrojový soubor obsahující funkci main :: IO (). Tato funkce je zavolána jako první po spuštění přeloženého programu. Výstupem je binární soubor, případně kód v C či assembleru. V překladači je kód interně reprezentován v jazyce C−−. Při překladu se můžeme setkat se soubory s těmito příponami:
.hs — zdrojový kód haskellového programu;.lhs — dokumentovaný (literární) zdrojový kód haskellového programu;.hspp — zdrojový kód, jež musí být nejprve prohnán preprocesorem (parametry -cpp, -E);.hi — rozhraní obsahující informace o exportovaných symbolech;.hc — výstup překladače v jazyce C (parametr -C);.s — výstup překladače v assembleru (parametr -S);.o — objektový soubor, který se dá připojit ke spustitelnému souboru (parametr -c).Parametry překladače GHC se v mnohém podobají céčkovému překladači GCC. Standardně můžeme přeložit program příkazem ghc soubor.hs -o výstup, pokud ale používáme nějakou knihovnu, tento příkaz se nevypořádá se závislostmi. Naštěstí má ale překladač parametr --make, který se o závislosti postará. Doporučuje se tedy překlad programu pomocí příkazu ghc --make soubor.hs. V tomto případě můžeme dokonce příponu souboru vynechat, tedy stačí napsat pouze ghc --make soubor.
Bývá zvykem soubory ve větším projektu pojmenovávat s počátečním velkým písmenem a jejich obsah rozčleňovat do modulů. Jak takové moduly fungují, si představíme na třetím cvičení. Pro více informací o překladu nahlédněte do manuálové stránky (man ghc) nebo do dokumentace překladače.
Pro většinu operací nám bude stačit interpret Haskellu ghci. Podobně jako v Hugsu do něj vlastní kód můžeme načíst pomocí příkazu :l soubor a obnovit ho pomocí :r. Rozdíl je však v načítání modulů. Příkaz pro přidávání dalších modulů je :m + Modul, pro odebírání :m - Modul. Při načtení většího množství modulů přestane být zadávání příkazu přehledné, v tom případě můžeme přenastavit prompt pomocí příkazu :set prompt "> ". Tabulátor doplňuje názvy funkcí. Všechny dostupné příkazy lze zobrazit pomocí :h.
Stejně jako v Hugsu zobrazíme typ výrazu příkazem :t. Pro vypsání podrobnějších informací o funkci (či datovém typu) slouží příkaz :i. Příjemnou změnou oproti Hugsu je možnost si definovat funkci přímo v interpretu pomocí příkazu let. Speciálním případem tohoto přiřazení je funkce it znázorňující výsledek posledního napsaného příkazu. V případě potřeby si můžeme všechna tato přiřazení vypsat pomocí příkazu :show bindings.
> let pi = 3.14 > let perimeter r = 2 * pi * r > perimeter 5 31.400000000000002 > :show bindings it :: Double = 31.400000000000002 perimeter :: Double -> Double = _ pi :: Double = 3.14 > 1 + 1 2 > it 2 > it * 10 20
Typické použití: chceme spustit soubor se zdrojovým kódem, ale nepotřebujeme ho mít v binární formě ani nechceme využívat možnosti interpretu. Po napsání příkazu runhaskell soubor.hs se zavolá funkce main v souboru soubor.hs. Ve skutečnosti se využívá programu runghc, příkaz runhaskell je jen symbolický odkaz na něj.
Haskell má relativně velkou komunitu, jejíž členové vytvářejí velké množství knihoven a různých nástrojů pro práci v Haskellu. Proto byl v roce 2004 spuštěn repozitář Hackage spolu s balíčkovacím systémem Cabal. Z tohoto repozitáře lze jednoduše stahovat a instalovat knihovny Haskellu pomocí cabalových balíčků. Asi nejjednodušší způsob pro získání přístupu k těmto balíčkům je nainstalovat si aplikaci Haskell Platform, jež obsahuje všechny důležité nástroje pro vývoj v Haskellu.
Balíčky v repozitáři Hackage můžeme procházet přímo, nebo je prohledávat pomocí dvou vyhledávačů:
Vyhledávač Hoogle (název je odvozen od Google) je starší ze dvou vyhledávačů. Umožňuje vyhledávání pomocí názvu funkce či jejího typu, bohužel však prohledává pouze několik základních knihoven. Vyniká svou jednoduchostí a přesnými výsledky vyhledávání.
Vyhledávač Hayoo (název je odvozen od Yahoo!) umožňuje v podstatě totéž co Hoogle, jenom prohledává celý repozitář Hackage, navíc přes moderní AJAXové rozhraní.
Tento pokročilý balíčkovací systém nám umožňuje přes nástroj cabal-install instalovat balíčky z Hackage přímo z příkazové řádky. Nemusíme se tak zabývat závislostmi ani nic sestavovat ručně. Veškerý instalovaný obsah se ukládá do adresáře ~/.cabal, případné spouštěcí soubory lze nalézt v adresáři ~/.cabal/bin. (Nastavte si proto vhodně proměnnou $PATH ve svém shellu, například přidáním řádku export PATH=$PATH:$HOME/.cabal/bin do souboru ~/.bashrc.) Seznam instalovaných balíčků je ukrytý v adresáři ~/.ghc, proto v případě odinstalování balíčku nestačí pouze smazat soubory, je nutné použít i příkaz ghc-pkg unregister. Příklad instalace balíčku:
$ cabal update Downloading the latest package list from hackage.haskell.org $ cabal install pureMD5 Resolving dependencies... Downloading pureMD5-2.1.0.3... Configuring pureMD5-2.1.0.3... Preprocessing library pureMD5-2.1.0.3... Preprocessing executables for pureMD5-2.1.0.3... Building pureMD5-2.1.0.3... [1 of 1] Compiling Data.Digest.Pure.MD5 ( Data/Digest/Pure/MD5.hs, dist/build/Data/Digest/Pure/MD5.o ) Registering pureMD5-2.1.0.3... Installing library in /home/xdvor/.cabal/lib/pureMD5-2.1.0.3/ghc-6.12.1 Registering pureMD5-2.1.0.3...
Příkaz cabal update stáhne aktuální seznam balíčků, příkaz cabal install balíček nainstaluje požadovaný balíček. Poskytnutý modul pak můžeme použít v našem programu:
$ cat md5-test.hs import Data.Digest.Pure.MD5 import Data.ByteString.Lazy.Char8 main :: IO () main = print . md5 $ pack "test" $ ghc --make md5-test [1 of 1] Compiling Main ( md5-test.hs, md5-test.o ) Linking md5-test ... $ ./md5-test 098f6bcd4621d373cade4e832627b4f6
V tomto příkladu je použita funkce md5 z knihovny Data.Digest.Pure.MD5, která slouží ke generování MD5 hašů. Jako vstup požaduje řetězec typu ByteString, jenž je vytvořen převodem z „obyčejného“ řetězce typu String pomocí funkce pack z knihovny Data.ByteString.Lazy.Char8.
Pro více informací o balíčkovacím systému Cabal se podívejte do jeho dokumentace.
Může se stát, že automatická instalace nebude z nějakého důvodu fungovat. V tom případě si můžete balíček stáhnout, rozbalit, přejít vytvořeného adresáře a napsat následující příkazy:
$ cabal configure $ cabal build $ cabal copy $ cabal register
Pokud nemáme cabal k dispozici, můžeme se pokusit balíček sestavit ručně. K tomu nám slouží tato trojice příkazů:
$ runhaskell Setup configure $ runhaskell Setup build $ runhaskell Setup install
Poslední příkaz musí být spuštěn pod administrátorským účtem. Pokud nemáme tuto možnost, lze balíček nainstalovat do domovského adresáře. V tomto případě bychom první příkaz nahradili za příkaz runhaskell Setup configure --user --prefix=$HOME.
Leksah je vývojové prostředí Haskellu. Lze ho používat na psaní domácích úkolů do tohoto předmětu. Instaluje se napsáním příkazu cabal install gtk2hs-buildtools && cabal install leksah (pozor, pro jeho provoz potřebujete zhruba 500 MB volného místa v domovském adresáři; aktuální stav na školních počítačích zjistíte pomocí příkazu quota -s). Ovládání této aplikace není přímočaré, pro více informací si pročtěte manuál k Leksahu.
Darcs je distribuovaný verzovací systém napsaný v Haskellu a používaný pro správu mnoha haskellových projektů. Svými vlastnostmi se podobá verzovacímu systému Git.
Lambdabot je užitečný pomocník při programování v Haskellu. Umí vyhodnocovat výrazy, určovat jejich typ, vyhledávat pomocí Hoogle, převádět na pointfree (pointless) tvar, zabrazovat zdrojový kód funkcí, generovat kód k daným typům, ověřovat platnost zadaných výrazů a mnoho dalších věcí. V základním nastavení se chová jako IRC bot.
Xmonad je minimalistický okenní správce, který spolu s lištou Xmobar tvoří tak trochu netradiční, avšak efektivní rozhraní pro ovládání osobního počítače běžícího na unixovém systému.