Opened 5 years ago

Closed 5 years ago

#2851 closed merge (fixed)

Improve error message for failed deriving

Reported by: guest Owned by: igloo
Priority: normal Milestone:
Component: Compiler (Type checker) Version: 6.10.1
Keywords: Cc: lennart@…
Operating System: Unknown/Multiple Architecture: Unknown/Multiple
Type of failure: Difficulty: Unknown
Test Case: deriving/should_fail/T2851 Blocked By:
Blocking: Related Tickets:

Description

The following does not work:

type family F a :: *

data D a = D (F a)
    deriving (Show)

The natural way of adding an instance does work (with enough extensions turned on):

instance (Show (F a)) => Show (D a) where
    show (D x) = "D " ++ show x

It would be nice if the deriving mechanism could derive this code.

Change History (9)

comment:1 Changed 5 years ago by guest

  • Cc lennart@… added

comment:2 Changed 5 years ago by simonpj

  • Difficulty set to Unknown
  • Resolution set to invalid
  • Status changed from new to closed

Well, it's tricky. The 'deriving' mechanism is supposed to produce nice, well-behaved, terminating instances, so it insists (as the H98 report says) on producing an instance context whose constraints are of the form (C a), where a is a type variable.

Fortunately, GHC has just what you want: standalone deriving. Try this:

{-# LANGUAGE TypeFamilies, FlexibleContexts, 
             UndecidableInstances, StandaloneDeriving #-}

type family F a :: *

data D a = D (F a)

deriving instance Show (F a) => Show (D a)

You get to specify the context for the instance, and GHC adds the code for the Show methods. Notice that you have to add FlexibleContexts and UndecidableInstances .... and rightly so. I find this approach works much better than requiring these flags for an instance declaration that the user never sees.

So I'll close this.

Simon

comment:3 Changed 5 years ago by guest

  • Component changed from Compiler to Compiler (Type checker)
  • Resolution invalid deleted
  • Status changed from closed to reopened
  • Summary changed from Deriving doesn't work when type families are involved to Improve error message for failed deriving

(I don't have a ghc-6.10 here to test, so maybe it's already good, but) It would be nice if, when deriving fails but standalone deriving might work, the error message would suggest to you to try standalone deriving. (and warn you what other extensions you might need. ...And ideally it would even suggest the whole deriving-line e.g.

deriving instance Show (F a) => Show (D a)

, but of course one of the issues is that GHC can't always even make a good guess at what you want the context to be.)

-Isaac Dupree

comment:4 Changed 5 years ago by guest

I did try 'deriving instance', but without the context. With a context it works like a charm.
But like Isaac says, it would be nice with a better error message, since it wasn't obvious to me that the 'deriving instance' would do the trick.

comment:5 Changed 5 years ago by simonpj

OK I'll think about that. Meanwhile, the user guide for standalone deriving should have told you about the need for a context. Yell if it needs to be improved. Simon

comment:6 Changed 5 years ago by guest

It would be an improvement if the error message just mentions standalone deriving, without giving the actual needed line of code.

comment:7 Changed 5 years ago by simonpj

  • Owner set to igloo
  • Status changed from reopened to new
  • Test Case set to deriving/should_fail/T2851
  • Type changed from feature request to merge

OK, I've done that

Tue Dec 30 16:59:06 GMT 2008  simonpj@microsoft.com
  * Improve error message in deriving (fix Trac #2851)

The error now says:

T2851.hs:8:14:
    No instance for (Show (F a))
      arising from the 'deriving' clause of a data type declaration
                   at T2851.hs:8:14-17
    Possible fix: add an instance declaration for (Show (F a))
    Alternative fix: use a standalone 'deriving instance' declaration instead,
      so you can specify the instance context yourself
    When deriving the instance for (Show (D a))

Please merge.

Simon

comment:8 Changed 5 years ago by simonpj

PS: I did a bit more, because the previous patch suggested the same fix for overlapping instances, which is misleading

Wed Dec 31 06:35:21 PST 2008  simonpj@microsoft.com
  * Improve error reporting for 'deriving'

Simon

comment:9 Changed 5 years ago by igloo

  • Resolution set to fixed
  • Status changed from new to closed

Both merged

Note: See TracTickets for help on using tickets.