理解 <$> 的签名
Understanding the signature of <$>
我或多或少地了解了应用程序 <$>
运算符,但我无法理解我在以下示例中获得的签名:
ghci> let f x y z = x + y + z -- f::Num a => a -> a -> a -> a
ghci> f <$> Just 2 <*> Just 3 <*> Just 4
Just 9
这个结果我明白了,但是在检查下面的类型时:
ghci> :t (<$> f)
(<$> f) :: Num a => ((a -> a -> a) -> b) -> a -> b --This makes no sense to me
那个签名我会理解为:一个以 (a -> a- > a) -> b
函数和 a
作为参数以及 returns 和 b
的函数。根据这个推理,我应该这样称呼它:
(<$>f) f 4
这将导致 Integer
。
显然这不是真的,所以你能帮我理解如何读取 (<$> f)
的类型吗?
a function that takes a (a -> a- > a) -> b
function and an a
as parameters and returns a b
.
这是正确的。
According to this reasoning , I should call this like :
(<$>f) f 4
which would result in an Integer
.
否,因为 f
没有类型 (a -> a -> a) -> b
或与之兼容的类型。相反,它的类型为 Num a => a -> a -> a -> a
。也就是说,f
接受三个数字并生成一个数字,而我们正在寻找一个将函数(a -> a -> a
类型)作为第一个参数的函数。
<$>
将类型为 g b
的东西作为第二个参数,其中 g
是任何应用函子。
您正在将 f :: Num a => a -> a -> a -> a
作为第二个参数传递。为了简单起见,让我们忽略 Num a
上下文。
因此,我们寻找 g,b
使得 g b = a -> a -> a -> a
.
让我们把f
的类型写成前缀形式:
f :: (->) a ((->) a ((->) a a)) = g b
因此,g = (->) a
和 b = ((->) a ((->) a a))
。后者是中缀形式的b = a -> a -> a
。
碰巧 (->) a
是一个应用函子,所以 <$> f
类型检查。但是请注意, <$>
用于与示例中使用的 Maybe
完全不同的仿函数。因此混乱。
TL;DR:重载的标识符可以变形为适应其上下文的许多事物,可能以某种意想不到的方式。
我或多或少地了解了应用程序 <$>
运算符,但我无法理解我在以下示例中获得的签名:
ghci> let f x y z = x + y + z -- f::Num a => a -> a -> a -> a
ghci> f <$> Just 2 <*> Just 3 <*> Just 4
Just 9
这个结果我明白了,但是在检查下面的类型时:
ghci> :t (<$> f)
(<$> f) :: Num a => ((a -> a -> a) -> b) -> a -> b --This makes no sense to me
那个签名我会理解为:一个以 (a -> a- > a) -> b
函数和 a
作为参数以及 returns 和 b
的函数。根据这个推理,我应该这样称呼它:
(<$>f) f 4
这将导致 Integer
。
显然这不是真的,所以你能帮我理解如何读取 (<$> f)
的类型吗?
a function that takes a
(a -> a- > a) -> b
function and ana
as parameters and returns ab
.
这是正确的。
According to this reasoning , I should call this like :
(<$>f) f 4
which would result in an
Integer
.
否,因为 f
没有类型 (a -> a -> a) -> b
或与之兼容的类型。相反,它的类型为 Num a => a -> a -> a -> a
。也就是说,f
接受三个数字并生成一个数字,而我们正在寻找一个将函数(a -> a -> a
类型)作为第一个参数的函数。
<$>
将类型为 g b
的东西作为第二个参数,其中 g
是任何应用函子。
您正在将 f :: Num a => a -> a -> a -> a
作为第二个参数传递。为了简单起见,让我们忽略 Num a
上下文。
因此,我们寻找 g,b
使得 g b = a -> a -> a -> a
.
让我们把f
的类型写成前缀形式:
f :: (->) a ((->) a ((->) a a)) = g b
因此,g = (->) a
和 b = ((->) a ((->) a a))
。后者是中缀形式的b = a -> a -> a
。
碰巧 (->) a
是一个应用函子,所以 <$> f
类型检查。但是请注意, <$>
用于与示例中使用的 Maybe
完全不同的仿函数。因此混乱。
TL;DR:重载的标识符可以变形为适应其上下文的许多事物,可能以某种意想不到的方式。