2013-08-20 31 views
1

Simon Peyton-Jones在他的演講「Classes,Jim,但並不像我們所知道的那樣」中談到了如何通過使多態函數採用額外參數來實現類型類,函數賦予函數的類型。多態函數的專業化

然後他說,GHC經常通過特殊外殼函數優化函數,而不是在運行時實際傳遞該字典。然後他說這並不總是可能的,因爲Haskell具有多態遞歸,所以即使你有整個程序,也不一定消除所有的多態性。

他是什麼意思?什麼是一個程序的例子,其中一個人不知道多態函數的類型將在編譯時傳遞?

回答

3

下面是一個典型的多態遞歸示例。比方說,我們也有類似的列表中的數據類型,但每一個元素都有一個類型兩倍的「大」與前一個:

data Poly a = Nil | Cons a (Poly (a,a)) deriving Show 

foo :: Poly Int 
foo = Cons 3 (Cons (4,5) (Cons ((6,7),(8,9)) Nil)) 

length' :: Poly a -> Int 
length' Nil = 0 
length' (Cons _ xs) = 1 + length' xs 

請注意,以length'遞歸調用已經從原來的呼叫不同的類型。

由於無法靜態地知道可能創建了哪些列表,因此我們無法從程序中刪除所有字典。

+0

因此,在這種情況下,討論*多態遞歸*時,它是遞歸的*數據類型* – beta

+5

@beta:不,多態遞歸發生在遞歸調用與開始時類型不同的函數時。 'f :: Show a => Int - > a - > String; f 0 x = show x; f n x = f(n - 1)[x]'是在普通列表上發生的多態遞歸。 – Vitus

+0

哎呀......實際上在示例中添加了一個多態遞歸函數。 – Fixnum