2008-12-05 17 views
20

Trochę pytania z haskellem neofita, ale natknąłem się na ten przykład w Haskella tutorial examples. Dla „znaleźć ostatni element listy” istnieją pewne oczywiste wersje, jakFunkcja funkcji Haskella

last' [x] = x 
last' (_:xs) = last' xs 

Ale nie mogę sensu z alternatywnej wersji przedstawiane:

myLast' = foldr1 (const id) 

Tak, próbując zrobić poczucie co stosowanie funkcji id robi, próbowałem w ghci:

const id 1 2 -> gives 2 

to wiąże się to tak:

(const id) 1 2 -> gives 2 

A nie tak:

const (id 1) 2 -> gives 1 

Ale nie mam sensu tego. (const id) powinno przełożyć się coś podobnego

`(\x y->x) (\x->x)` 

Gdyby nie to powrót funkcję, która po prostu zwraca identyfikator swojego pierwszego elementu? Lub w jaki sposób tworzenie kolejności funkcji (const id) zachowuje się inaczej niż const?

+1

Witamy w klubie 10k! –

+3

Chciałbym podziękować akademii, mojemu producentowi, reżyserowi ... –

+0

loooooooool! Like: P – Nomics

Odpowiedz

30

Definicja const jest

const x = \_ -> x 

Stąd (const id) jest funkcją, która przyjmuje jeden argument i zwraca id i

const id 1 2 = (\_ -> id) 1 2 
      = id 2 
      = 2 

Definicja foldr1 jest

foldr1 f [x] = x 
foldr1 f (x:xs) = f x (foldr1 f xs) 

Jeśli mamy

myLast' = foldr1 (const id) 

następnie

myLast' [x] = foldr1 (const id) [x] 
       {- definition of foldr1 -} 
      = x 

i

myLast' (x:xs) = foldr1 (const id) (x:xs) 
       {- definition of foldr1 -} 
       = (const id) x (foldr1 (const id) xs) 
       {- definition of const -} 
       = (\_ -> id) x (foldr1 (const id) xs) 
       {- function application -} 
       = id (foldr1 (const id) xs) 
       {- definition of id -} 
       = foldr1 (const id) xs 
       {- definition of myLast' -} 
       = myLast' xs 

która zgadza się z definicją last'.

+1

ahhh. Nie nawiązał połączenia z const zwracającą funkcję. Dziękuję za wyjaśnienie. –

+0

To jest świetne wyjaśnienie i przechodząc przez to, widzę, jak to działa. Ale czy foldr1 (const id) jest naprawdę idiomatycznym sposobem wykonywania funkcji myLast? Pierwszy podany przykład wydaje się wyraźniejszy ... –

+2

Nie powiedziałbym, że jest idiomatyczny ...Haskellowcy lubią pracować nad tym, jak wyrazić rzeczy w stylu "bez punktów", lub w kategoriach fałd. Staje się swoistą zagadką programowania. Pierwsza wersja jest o wiele bardziej przejrzysta. –

9

Podczas próby zrozumienia Haskella polegam głównie na :t. W takim przypadku:

Prelude> :t const id 
const id :: b -> a -> a

może pomóc Ci zobaczyć, co się dzieje.

+3

Aby wyjaśnić, ": t" jest poleceniem, którego można użyć w GHCI, aby wydrukować typ wyrażenia. –

Powiązane problemy