我正试图找到类型,(\x y z -> x . y z)但没有找到与ghci相同类型的任何成功
(\x y z -> x . y z) :: (b -> c) -> (t -> a -> b) -> t -> a -> c
Run Code Online (Sandbox Code Playgroud)
删除中缀函数并获取后(\x y z -> (.) x (y z)),我不知道如何继续.
向后工作,并指定类型变量,直到指定它们:
-- We assign types one by one:
(.) x (y z) :: a -- So,
(y z) :: b
(.) x :: b -> a
x :: c
(.) :: c -> b -> a
Run Code Online (Sandbox Code Playgroud)
但我们知道(.) :: (y -> z) -> (x -> y) -> (x -> z),所以,我们可以将某些类型等同于~:
c ~ y -> z
b ~ x -> y
a ~ x -> z
Run Code Online (Sandbox Code Playgroud)
我们现在知道:
x :: y -> z
(.) x (y z) :: x -> z
y z :: x -> y
Run Code Online (Sandbox Code Playgroud)
所以
z :: d
y :: d -> x -> y
Run Code Online (Sandbox Code Playgroud)
最后,我们只需完成函数的类型
-- (type of x) (Type of y) (type of z) (return type)
(\x y z -> x . y z) :: (y -> z) -> (d -> x -> y) -> d -> (x -> z)
Run Code Online (Sandbox Code Playgroud)
最后,我们可以要求GHCi确认:
Prelude> :t (\x y z -> x . y z)
(\x y z -> x . y z) :: (b -> c) -> (t -> a -> b) -> t -> a -> c
Run Code Online (Sandbox Code Playgroud)
我们可以扩展表达式\x y z -> x . y z如下:
\x y z -> x . y z
? \x y z w -> x (y z w) -- because (f . g) ? (\x -> f (g x))
? \f g x y -> f (g x y) -- renaming the variables
Run Code Online (Sandbox Code Playgroud)
现在,我们可以看看类型:
x :: a1
y :: a2
-- Because g is applied to x and y:
g :: (a1 -> a2 -> b)
-- Because f is applied to (g x y):
f :: (b -> c)
-- Therefore:
(\f g x y -> f (g x y)) :: (b -> c) -> (a1 -> a2 -> b) -> a1 -> a2 -> c
-- ???????? ??????????????? ? ?
-- f g x y
Run Code Online (Sandbox Code Playgroud)
如你所见,这个函数只是组成f和g:
????????? ?????????
x :: a1 ??? ? ? ?
? g ??? b ??? f ??? c
y :: a2 ??? ? ? ?
????????? ?????????
Run Code Online (Sandbox Code Playgroud)
有关更多信息,请查看以下问题和答案:(f.).在Haskell中意味着什么?