1
我有以下Haskell代碼失敗的Couldn't match type ‘a’ with ‘a1’
錯誤:不匹配剛性類型變量
bar :: [Int] -> (a -> Int -> a) -> a -> a
bar ns fp ap = snd $ foldl fn (fp, ap) ns
where fn :: ((a -> Int -> a), a) -> Int -> ((a -> Int -> a), a)
fn (f, x) i = (fp, (f x (i + length(ns))))
下面是詳細的錯誤信息:
t.hs:4:24: error:
• Couldn't match type ‘a’ with ‘a1’
‘a’ is a rigid type variable bound by
the type signature for:
bar :: forall a. [Int] -> (a -> Int -> a) -> a -> a
at t.hs:1:8
‘a1’ is a rigid type variable bound by
the type signature for:
fn :: forall a1.
(a1 -> Int -> a1, a1) -> Int -> (a1 -> Int -> a1, a1)
at t.hs:3:15
Expected type: a1 -> Int -> a1
Actual type: a -> Int -> a
• In the expression: fp
In the expression: (fp, (f x (i + length (ns))))
In an equation for ‘fn’:
fn (f, x) i = (fp, (f x (i + length (ns))))
• Relevant bindings include
x :: a1 (bound at t.hs:4:16)
f :: a1 -> Int -> a1 (bound at t.hs:4:13)
fn :: (a1 -> Int -> a1, a1) -> Int -> (a1 -> Int -> a1, a1)
(bound at t.hs:4:9)
ap :: a (bound at t.hs:2:11)
fp :: a -> Int -> a (bound at t.hs:2:8)
bar :: [Int] -> (a -> Int -> a) -> a -> a (bound at t.hs:2:1)
我在想,功能fp
參數bar
具有相同類型的f
參數f結fn
在功能bar
(它們都具有類型(a -> Int -> a)
)where
子句,然而ghci
處理它們作爲不同類型(a
和a1
)。
我試圖刪除函數的類型簽名fn
然後代碼可以成功編譯。
bar :: [Int] -> (a -> Int -> a) -> a -> a
bar ns fp ap = snd $ foldl fn (fp, ap) ns
where fn (f, x) i = (fp, (f x (i + length(ns))))
我的問題是:爲什麼的fn
額外的類型簽名不工作?是不是足夠智能的類型系統推斷fp
和f
可以有相同的類型? (特別是當fn
在bar
的範圍內)。
您需要啓用'ScopedTypeVariables'(併爲類型簽名添加一個顯式全部) - 否則兩個類型簽名引用不同類型的變量,這兩個變量都恰好被命名爲'a'。 – user2407038