2

I have just formulated the type of (.), generalized, as far as I can tell, however, upon typing it into Hoogle, I received no results.

I'd have expected

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

to match

thistype ~ f (f b c) (f (f a b) (f a c))
schuelermine
  • 1,958
  • 2
  • 17
  • 31
  • At a guess, hoogle does not allow `f` to specialise to `->`. What if you had a type family `X` such that `X a b c` was the type of `(.)`. Then you can’t really expect hoogle to match `f a b c` with `(.)` merely because `X` could be so defined. – Dan Robertson Aug 25 '18 at 17:30
  • @DanRobertson Well, I'd say the reason that wouldn't work is because you aren't allowed to say `f ~ X` anyway. You *are* allowed to say `f ~ (->)`. Indeed, if I look up [`:: a -> f a`](https://www.haskell.org/hoogle/?hoogle=%3A%3A+a+->+f+a), I get the usual suspects, plus a ton of results for various specializations of `f`, like `f ~ Identity` or `f ~ parsec:Consumed`. You are probably correct in saying that Hoogle doesn't like to specialize type constructors to `(->)`, but the rationale given doesn't seem right. – HTNW Aug 25 '18 at 21:29
  • Why is `f ~ X` not allowed? Do you mean that in `f ~ (->)`, `(->)` is a type constructor but `X` being a type family does not count? I think the real answer anyway is that hoogle treats functions in a special way so that searches can reorder arguments. Note that `f b c -> f a b -> f a c` will find `(.)` for categories, but still not specialised to functions. – Dan Robertson Aug 25 '18 at 21:36

1 Answers1

3

The technical answer is that Hoogle splits the search into arguments and return types on the outer (->) parts, and then searches for each part individually, before combining the results. The outer (->) is treated very specially, in particular it's happy to reorder arguments.

The more fundamental reason why Hoogle works this way is that it's a search engine, not a unification engine. If you were searching for the above, and got back (.), would that have answered your question? My guess is probably not. My favourite example is that searching for "a -> [(a,b)] -> b" should return lookup, even though it doesn't unify.

schuelermine
  • 1,958
  • 2
  • 17
  • 31
Neil Mitchell
  • 9,090
  • 1
  • 27
  • 85