Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
343 views
in Technique[技术] by (71.8m points)

Haskell function composition operator of type (c→d) → (a→b→c) → (a→b→d)

Ordinary function composition is of the type

(.) :: (b -> c) -> (a -> b) -> a -> c

I figure this should generalize to types like:

(.) :: (c -> d) -> (a -> b -> c) -> a -> b -> d

A concrete example: calculating difference-squared. We could write diffsq a b = (a - b) ^ 2, but it feels like I should be able to compose the (-) and (^2) to write something like diffsq = (^2) . (-).

I can't, of course. One thing I can do is use a tuple instead of two arguments to (-), by transforming it with uncurry, but this isn't the same.

Is it possible to do what I want? If not, what am I misunderstanding that makes me think it should be possible?


Note: This has effectively already been asked here, but the answer (that I suspect must exist) was not given.

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

My preferred implementation for this is

fmap . fmap :: (Functor f, Functor f1) => (a -> b) -> f (f1 a) -> f (f1 b)

If only because it is fairly easy to remember.

When instantiating f and f1 to (->) c and (->) d respectively you get the type

(a -> b) -> (c -> d -> a) -> c -> d -> b

which is the type of

(.) . (.) ::  (b -> c) -> (a -> a1 -> b) -> a -> a1 -> c

but it is a bit easier to rattle off the fmap . fmap version and it generalizes to other functors.

Sometimes this is written fmap fmap fmap, but written as fmap . fmap it can be more readily expanded to allow more arguments.

fmap . fmap . fmap 
:: (Functor f, Functor g, Functor h) => (a -> b) -> f (g (h a)) -> f (g (h b))

fmap . fmap . fmap . fmap 
:: (Functor f, Functor g, Functor h, Functor i) => (a -> b) -> f (g (h (i a))) -> f (g (h (i b))

etc.

In general fmap composed with itself n times can be used to fmap n levels deep!

And since functions form a Functor, this provides plumbing for n arguments.

For more information, see Conal Elliott's Semantic Editor Combinators.


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...