Is there a pretty/glib way to restrict a curry-ed function to the graph of another function in Haskell?

眉间皱痕 提交于 2020-05-31 04:55:34

问题


I finally got bored enough in quarantine to start learning Haskell today and I'm really enjoying myself, I really love the aesthetics of the language. Hopefully this question doesn't inspire any hate if it has already been posted here before, etc. It's very simple, but I'm an absolute beginner.

I've been trying to understand how to do some simple things elegantly (or at least in a so-called "point free" way) with the language and came upon the problem of how to describe in a clean way the procedure of taking a function of two variables and restricting it to the graph of a function between the two variables. E.g. how to take a function of two variables of the same type and restrict it along the diagonal to obtain a function of one variable with the same type and the same type of outputs, or any similar problem (a bit like trying currying on the wrong side of the hom, if you like).

I was messing around today with concise ways of doing this but eventually gave up and implemented the following for later use:

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

compFtn f g a = f a (g(a)) 

which does what I wanted (as would, say, decurrying f and doing this in a really ugly fashion). However I have a feeling that there must be a way more "point free"/doctrinaire solution to this very basic operation, so I'm here asking around to learn some style from y'all. Cheers.


回答1:


A function is a functor, an applicative and a monad. We may consider functions as a context with a contained value revealed once applied.

So for a function type Functor instance would be the composition (.) operator. Why? Lets say we have a function (+1) which says when you apply me a Num a class value i will increment it by 1. So lets implement fmap.

fmap f g = f . g -- <$> == (.)

obviously we are applying f to the return value of g.

So how can we make a function an instance of Applicative? It must contain another function in its context. Basically it should return a function when applied. This means (a -> b -> c) at least. So here you go.

(a -> b -> c) <*> (a -> b) is in fact once a is applied (a -> b -> c) becomes (b -> c) and (a -> b) becomes b and (b -> c) gets applied with the b. So yes what you are looking for is <*> operator.



来源:https://stackoverflow.com/questions/61907072/is-there-a-pretty-glib-way-to-restrict-a-curry-ed-function-to-the-graph-of-anoth

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!