简化Haskell型签名
我的问题是如何分析处理Haskell类型签名。为了使其具体化,我正在研究“修复”函数:简化Haskell型签名,haskell,types,Haskell,Types,我的问题是如何分析处理Haskell类型签名。为了使其具体化,我正在研究“修复”函数: fix :: (a -> a) -> a 还有一个我写的用来做花生加法的小函数: add = \rec a b -> if a == 0 then b else rec (a-1) (b+1) 当我检查类型时,我得到了fix add的预期类型: fix add :: Integer -> Integer -> Integer 而且它似乎像我期望的那样工作: > (fi
fix :: (a -> a) -> a
还有一个我写的用来做花生加法的小函数:
add = \rec a b -> if a == 0 then b else rec (a-1) (b+1)
当我检查类型时,我得到了fix add
的预期类型:
fix add :: Integer -> Integer -> Integer
而且它似乎像我期望的那样工作:
> (fix add) 1 1
2
如何使用
fix
和add
的类型签名来显示fix add
具有上述签名?如果“代数”这个词是正确的,那么使用类型签名的规则是什么?我怎样才能“展示我的作品”ghci
告诉我们
add::Num a=>(a->a->a)->a->a->a
对某些类型类噪波进行模化,因为add
的第二个参数需要一个Eq
实例(您正在检查它是否与0
相等)
当我们将fix
应用于add
时,fix
的签名变为
fix::((a->a->a)->(a->a->a))->(a->a->a)
请记住,fix:(a->a)->a
中的a
s可以具有任何类型。在这种情况下,它们的类型为(a->a->a)
因此,fixadd::numa=>a->a->a
,这正是添加两个a
s的正确类型
您可以以非常代数的方式使用Haskell的类型签名,变量替换的工作方式与您预期的一样。事实上,类型和代数之间有着直接的联系。谢谢!我已经计算出了很多(在
fix
中a
必须是(a->a->a)
)。但难道一步也没有走完吗?在((a->a->a)->(a->a->a))->(a->a->a)
和a->a
之间是否存在某种中间环节?是的,您部分地将fix
应用于add
。结果部分应用的函数具有类型a->a
@twopoint718将fix
应用到add
会从fix
的类型中删除((a->a->a->a))
参数。@GabrielGonzalez谢谢,我想这样做了。我现在明白了。谢谢大家。