[Haskell-beginners] Understanding the type signature of flip$id

Jeff Lasslett jeff.lasslett at gmail.com
Wed Mar 2 06:33:17 CET 2011


Thanks Daniel,

I think I follow what you've written.

(b -> c) -> (b -> c) is the same as (b -> c) -> b > c

and when that is flipped: b -> (b- > c) -> c

Is that right?

Thanks,
Jeff



On 2 March 2011 11:23, Daniel Fischer <daniel.is.fischer at googlemail.com> wrote:
> On Wednesday 02 March 2011 00:43:23, Jeff Lasslett wrote:
>>  I just don't understand how passing id to flip results in the
>> following type signature:
>>
>> Prelude> :t flip$id
>> flip$id :: b -> (b -> c) -> c
>>
>> I do understand what flip has done to map here:-
>>
>> Prelude> :t flip$map
>> flip$map :: [a] -> (a -> b) -> [b]
>>
>> map take a function and a list and produces a new list.  If map is
>> passed to flip the result is a function that takes a list, then a
>> function and results in a new list.
>>
>> How do we go from flip having this signature:
>>
>> Prelude> :t flip
>> flip :: (a -> b -> c) -> b -> a -> c
>> Prelude>
>>
>> and id having
>>
>> Prelude> :t id
>> id :: a -> a
>> Prelude>
>>
>> to flip$id looking like flip$id :: b -> (b -> c) -> c   ???
>>
>> Thanks,
>> Jeff
>
> The point is that the type of id has to be unified with the type of flip's
> (first) argument.
>
> flip :: (a -> b -> c) -> (b -> a -> c)
> id :: t -> t
>
> So we have to unify (a -> b -> c) and (t -> t). Fully parenthesized,
> a -> b -> c is a -> (b -> c). Now unification yields
>
> t = a
> -- id's arg must have the same type as the flip's argument's arg
>
> and
>
> t = (b -> c)
> -- id's result must have the same result as flip's argument's result
>
> From that follows a = (b -> c) and *id can be passed to flip only at a more
> restricted type than id's most general type, namely at the type
> id :: (b -> c) -> (b -> c)*
>
> So,
>
> flip (id :: (b -> c) -> b -> c) :: b -> (b -> c) -> c
>



More information about the Beginners mailing list