[GHC] #10086: Disambiguate type variables using dictionaries

#10086: Disambiguate type variables using dictionaries -------------------------------------+------------------------------------- Reporter: jstolarek | Owner: Type: feature | Status: new request | Milestone: Priority: normal | Version: 7.11 Component: Compiler | Operating System: Unknown/Multiple (Type checker) | Type of failure: Other Keywords: | Blocked By: Architecture: | Related Tickets: Unknown/Multiple | Test Case: | Blocking: | Differential Revisions: | -------------------------------------+------------------------------------- Consider this code: {{{#!hs type family TF t type instance TF (Maybe a) = Maybe a class Id f where idTF :: TF f -> TF f instance Id (Maybe a) where idTF x = x g = idTF (Just 'c') }}} Definition of `g` is rejected due to ambiguity: {{{ Couldn't match expected type ‘TF f0’ with actual type ‘Maybe Char’ The type variable ‘f0’ is ambiguous Relevant bindings include g :: TF f0 (bound at T6018.hs:18:1) In the first argument of ‘idTF’, namely ‘(Just 'c')’ In the expression: idTF (Just 'c') }}} There are two ways to proceed: 1. Introduce `Proxy` argument and disambiguate `f` with explicit type annotation. 2. With injective type families (coming Real Soon Now) we can declare `TF` as injective and this code will compile. That obviously won't work if `TF` is not injective. I think we could do better here. `idTF` is a type class function and when it is called GHC uses a concrete implementation from a dictionary. But notice that if we have the dictionary we could equally well use it to disambiguate `f`. In this example we call `idTF` with a `Maybe Char` argument, which means we are using `Id (Maybe a)` instance. Knowing this we could infer that `f` is `Maybe a`. -- Ticket URL: http://ghc.haskell.org/trac/ghc/ticket/10086 GHC http://www.haskell.org/ghc/ The Glasgow Haskell Compiler

#10086: Disambiguate type variables using dictionaries -------------------------------------+------------------------------------- Reporter: jstolarek | Owner: Type: feature request | Status: new Priority: normal | Milestone: Component: Compiler (Type | Version: 7.11 checker) | Keywords: Resolution: | Architecture: Operating System: Unknown/Multiple | Unknown/Multiple Type of failure: Other | Test Case: Blocked By: | Blocking: Related Tickets: | Differential Revisions: -------------------------------------+------------------------------------- Comment (by rwbarton):
In this example we call idTF with a Maybe Char argument, which means we are using Id (Maybe a) instance.
But you can't infer that because there could be another instance `TF (Either Int a) = Maybe a` that you can't see. Or put differently, adding a new (compatible) instance for a type family is not supposed to break any uses of that type family. If `TF` was a closed type family, then perhaps GHC could make this sort of inference. It amounts to checking injectivity "locally" for particular types as needed: i.e. check not that `TF x = y` has at most one solution for every `y`, but just for the particular `y` that is needed. -- Ticket URL: http://ghc.haskell.org/trac/ghc/ticket/10086#comment:1 GHC http://www.haskell.org/ghc/ The Glasgow Haskell Compiler

#10086: Disambiguate type variables using dictionaries -------------------------------------+------------------------------------- Reporter: jstolarek | Owner: Type: feature request | Status: closed Priority: normal | Milestone: Component: Compiler (Type | Version: 7.11 checker) | Keywords: Resolution: invalid | Architecture: Operating System: Unknown/Multiple | Unknown/Multiple Type of failure: Other | Test Case: Blocked By: | Blocking: Related Tickets: | Differential Revisions: -------------------------------------+------------------------------------- Changes (by jstolarek): * status: new => closed * resolution: => invalid Comment: Looks like you're right. I'll close this as invalid. -- Ticket URL: http://ghc.haskell.org/trac/ghc/ticket/10086#comment:2 GHC http://www.haskell.org/ghc/ The Glasgow Haskell Compiler
participants (1)
-
GHC