无法理解currying

vin*_*ngo 1 haskell

从理论上讲,我理解currying是什么,但实际上我对ghci中的内容感到困惑.

我们来看下面的例子.首先是我要使用的类型.

Prelude> :t f
f :: a -> a -> a -> a

Prelude> :t x
x :: char

Prelude> :t y
y :: char -> char

Prelude> :t z
z :: char -> char -> char
Run Code Online (Sandbox Code Playgroud)

通过以下操作,您能告诉我如何获得这些类型吗?

Prelude> :t f x
f x :: a -> a -> a

Prelude> :t f y
f y :: (char -> char) -> (char -> char) -> char -> char

Prelude> :t f z
f z
  :: (char -> char -> char)
     -> (char -> char -> char) -> char -> char -> char
Run Code Online (Sandbox Code Playgroud)

Wil*_*sem 6

:该char类型的参数,是不是一个CharACTER.由于它以小写字母开头,因此它是一个类型参数.x因此x :: b也是这种类型.

Haskell中的函数只有一个参数.如果有人写道:

f :: a -> a -> a -> a
Run Code Online (Sandbox Code Playgroud)

那么这实际上是:

f :: a -> (a -> (a -> a))
Run Code Online (Sandbox Code Playgroud)

所以f接受一个类型的参数a,并返回一个类型的函数a -> (a -> a).

f x :: a -> a -> a

如果我们想要派生类型f x,我们可以看到:

f :: a -> (a -> (a -> a))
x :: b
Run Code Online (Sandbox Code Playgroud)

因为x是具有fas函数的函数应用程序的参数,所以它意味着x(b)的类型应该与函数(a)的参数类型相同.所以它意味着a ~ b(和a它的类型相同b).

结果的类型是函数输出的类型,所以a -> (a -> a),或b -> (b -> b).但由于b并不是更具体a,两者都很好.

一个不那么冗长的表达a -> (a -> a)a -> a -> a.

f y :: (b -> b) -> (b -> b) -> b -> b

那怎么样f y?作为成分,我们有:

f :: a -> (a -> (a -> a))
y :: b -> b
Run Code Online (Sandbox Code Playgroud)

由于y是具有功能的应用程序的参数f的类型,y(b -> b)是相同的类型a,这样就意味着a ~ (b -> b).

因此输出类型是:

f y :: a -> (a -> a)
Run Code Online (Sandbox Code Playgroud)

或者当我们转换它时:

f y :: (b -> b) -> ((b -> b) -> (b -> b))
Run Code Online (Sandbox Code Playgroud)

或者更简洁:

f y :: (b -> b) -> (b -> b) -> b -> b
Run Code Online (Sandbox Code Playgroud)

f z :: (b -> b -> b) -> (b -> b -> b) -> b -> b -> b

作为我们的成分:

f :: a -> (a -> (a -> a))
z :: b -> (b -> b)
Run Code Online (Sandbox Code Playgroud)

这意味着对于功能应用程序f z,我们就这样了a ~ (b -> (b -> b)).结果是类型f z是:

f z :: a -> (a -> a)
Run Code Online (Sandbox Code Playgroud)

或当我们转换a(b -> (b -> b)):

f z :: (b -> (b -> b)) -> ((b -> (b -> b)) -> (b -> (b -> b)))
Run Code Online (Sandbox Code Playgroud)

或者更简洁:

f z :: (b -> b -> b) -> (b -> b -> b) -> b -> b -> b
Run Code Online (Sandbox Code Playgroud)