Vielä laskentoa: kertausta ja täsmennystä TIEA341 Funktio-ohjelmointi 1 Syksy 2005
“Laajennetun aritmetiikan” lausekkeet Muuttuja on lauseke Ei-negatiivinen lukuvakio on lauseke Kahden lausekkeen summa, erotus, tulo ja osamäärä ovat lausekkeita, samoin lausekkeen vastaluku Funktiokutsu on lauseke funktion nimi jonka jälkeen tulee peräkkäin kirjoitettuna yksi tai useampi argumenttilauseke Koostimenkutsu on lauseke muodoltaan kuten funktiokutsu koostin eroaa funktion nimestä isolla alkukirjaimellaan Haskellin case on lauseke rajoitus: ei vahteja, hahmot eivät rekursiivisia Pohja (⊥) on lauseke – ilmaisee virhettä
Presedenssi ja assosiatiivisuus Huom! f g h x on sama kuin ((f g) h) x
Normaalimuodot Heikko päänormaalimuoto (WHNF): Vakio on WHNF-lauseke Koostimenkutsu on WHNF-lauseke Vastalukulauseke on WHNF Pohja on WHNF-lauseke Normaalimuoto (NF): Vakio on NF-lauseke Koostimenkutsu on NF-lauseke, jos sen argumenttilausekkeet ovat NF huomaa rekursiivinen määrittely! Vastalukulauseke on NF, jos sen alilauseke on vakio Pohja on NF-lauseke
Vastaluvun sievennyssääntö (NEG) Lauseke on NEG-redeksi, jos se on vastalukulauseke e ja e on WHNF ja e ei ole vakio NEG-redeksi sievenee aina pohjaksi Huom! Vakion vastaluku on normaalimuodossa, sitä ei voi sieventää
Yhteen-, vähennys- ja kertolaskun sievennys (+, -, *) Lauseke on +-, - tai *-redeksi, jos se on yhteen-, vähennys-, tai kertolasku ja sen alilausekkeet ovat WHNF Jos molemmat alilausekkeet ovat vakioita, +-, - ja *-redeksi sievenee normaalisti nollalla jako tuottaa pohjan Jos toinen alilauseke on vastalukulauseke: e + (e') ==> e e', e (e') ==> e + e' (e) + e' ==> e' e, (e) e' ==> e' + e e * (e') ==> (e * e'), e / (e') ==> (e / e') (e) * e' ==> (e * e'), (e) / e' ==> (e / e') (e) * (e') ==> e * e', (e) / (e') ==> e / e' Muuten tulos on pohja
Funktiokutsun sievennys Funktiokutsulauseke f e1 ... en on aina funktiokutsuredeksi Jos laskentaympäristössä on f x1 ... xn = e huomaa: sama määrä parametreja kuin argumentteja niin lauseke sievenee muotoon e[x1e1,...,xnen] Jos ei, niin lauseke sievenee pohjaksi
Casen sievennys, tapaus 1 case-lauseke on LCASE-redeksi, jos sen ensimmäinen hahmo on muuttujahahmo case e of x -> e' sievenee muotoon e[xe] huomaa! sovitettavan ei tarvitse olla WHNF! poikkeus viime viikon säännöstä
Casen sievennys, tapaus 2 case-lauseke on ECASE-redeksi, jos se ei ole LCASE-redeksi ja tutkittava lauseke on WHNF jos casessa ei ole hahmoja, lauseke sievenee pohjaksi case C e1 ... en of C x1 ... xn -> e sievenee muotoon e[x1e1,...,xnen] sama koostin, sama määrä parametreja ja argumentteja case V of V -> e sievenee muotoon e muuten case e of p1 -> e1 ; p2 -> e2 ... sievenee muotoon case e of p2 -> e2 ...
Korvaus e[x1e1,...,xnen] Pääsääntö: kukin muuttuja xi korvataan ei:llä lausekkeessa e Poikkeus: jos jokin xi on jossakin alilausekkeessa paikallinen muuttuja (case-lausekkeiden haarat lähinnä), näitä paikallisia muuttujia ei korvata Varoitus: Korvaus ei saa aiheuttaa ei-paikallisen muuttujan muuttumista paikalliseksi paikallinen muuttuja on nimettävä uudelleen konfliktin sattuessa esim. (case 1 of x -> y)[yx] ==> case 1 of z -> x
Sievennettävän alilausekkeen valinta Jos lausekkeessa on useampi redeksi, valitaan niistä vasemmanpuoleisin jätetään huomiotta ne redeksit, jotka ovat toisen redeksin sisällä Toisin sanoen: uloimmista vasemmanpuolisin ... eli normaalijärjestys
Viimeinen sievennyssääntö Jos lausekkeella ei muiden sääntöjen nojalla ole normaalimuotoa, se voidaan viimeisen sievennyssäännön nojalla sieventää pohjaksi Pohja edustaa näin ollen sekä virhettä että umpiluuppia puhtaassa funktio-ohjelmoinnissa ohjelma ei muutenkaan voi erottaa näitä toisistaan