gpt4 book ai didi

haskell - 理解 Haskell 的 RankNTypes

转载 作者:行者123 更新时间:2023-12-02 18:50:44 24 4
gpt4 key购买 nike

在研究 GHC 扩展时,我遇到了 RankNTypes at the School of Haskell ,其中有以下示例:

main = print $ rankN (+1)

rankN :: (forall n. Num n => n -> n) -> (Int, Double)
rankN f = (f 1, f 1.0)

文章提供了 rankN 的替代类型:

rankN :: forall n. Num n => (n -> n) -> (Int, Double) 

差异的解释是

The latter signature requires a function from n to n for some Num n; the former signature requires a function from n to n for every Num n.

我可以理解,前一种类型要求签名是括号中或更通用的签名。我不明白后一个签名只需要一个函数 n -> n 来表示“some Num n”的解释。有人可以详细说明和澄清吗?您如何“阅读”这个以前的签名,使其听起来像它的意思?后一个签名是否与简单的 Num n => (n -> n) -> (Int, Double) 相同,而不需要 forall

最佳答案

在正常情况下( forall n. Num n => (n -> n) -> (Int, Double) ),我们选择 n 首先然后提供一个函数。所以我们可以传入 Int -> Int 类型的函数, Double -> Double , Rational -> Rational等等。

在 Rank 2 情况 ( (forall n. Num n => n -> n) -> (Int, Double) ) 中,我们必须在我们知道 n 之前提供函数 。这意味着该函数必须适用于任何 n ;我为上一个示例列出的所有示例都不起作用。

我们需要这个作为示例代码,因为函数 f传入的值应用于两种不同的类型: Int和一个 Double 。所以它必须对他们双方都有效。

第一种情况是正常的,因为这就是类型变量默认的工作方式。如果您没有forall无论如何,您的类型签名相当于一开始就有它。 (这称为 prenex 形式。)所以 Num n => (n -> n) -> (Int, Double)隐式与 forall n. Num n => (n -> n) -> (Int, Double) 相同.

适用于任何的函数类型是什么n ?正是forall n. Num n => n -> n .

关于haskell - 理解 Haskell 的 RankNTypes,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/33446759/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com