[GHC] #1749: forall type gives "not polymorphic enough" error incorrectly

GHC trac at haskell.org
Sat Sep 29 17:11:22 EDT 2007


#1749: forall type gives "not polymorphic enough" error incorrectly
----------------------------------------+-----------------------------------
    Reporter:  guest                    |        Owner:         
        Type:  bug                      |       Status:  closed 
    Priority:  normal                   |    Milestone:         
   Component:  Compiler (Type checker)  |      Version:  6.6.1  
    Severity:  normal                   |   Resolution:  invalid
    Keywords:                           |   Difficulty:  Unknown
          Os:  Windows                  |     Testcase:         
Architecture:  x86                      |  
----------------------------------------+-----------------------------------
Changes (by simonpj):

  * status:  new => closed
  * resolution:  => invalid

Comment:

 As Stefan says, this is our old friend the Monomorphism Restriction.  Look
 at the defn of `sf`.  Nothing says that it has anything to do with the ST
 monad, so it's most general type (which GHC infers) is
 {{{
   sf :: forall m. Monad m => b -> m c
 }}}
 Since that would be a constrained type, the MR kicks in, and it really
 gets the type
 {{{
   sf :: b -> m c
 }}}
 Later GHC discovers that `m = ST s`, but it's too late: `sf` is in the
 environment, monomorphic in `m`, and that means it's insufficiently
 polymorphic to be an argument to `SF`.

 This doesn't happen in the defn of `sfCompose` becuase the `runSF` calls
 specify that `m = ST s`, and that's enough to simplify away
 the `Monad` constraint, so MR does not kick in, so
 the defn can be generalised.

 This is a nice example of the MR hurting in an unexpected way.  I think
 it'd be good to collect such examples, so I've started a collection on the
 [http://www.haskell.org/haskellwiki/Monomorphism_restriction main
 HaskellWiki MR page].

 Meanwhile, your best bet is a type signature, only you can do it a bit
 less clumsily using a `forall` to bring the type variables into scope
 {{{
 sfPure2 :: forall b c. (b -> c) -> SF b c
 sfPure2 f = SF sf where
      sf :: forall s. ST s (SFST s b c)
      sf = return $ \b -> return (f b)
 }}}
 Or you could just inline `sf`!

 Simon

-- 
Ticket URL: <http://hackage.haskell.org/trac/ghc/ticket/1749#comment:3>
GHC <http://www.haskell.org/ghc/>
The Glasgow Haskell Compiler


More information about the Glasgow-haskell-bugs mailing list