Opened 8 years ago

Closed 7 years ago

Last modified 3 years ago

#5936 closed feature request (fixed)

Support for data families in generics

Reported by: reinerp Owned by: dreixel
Priority: normal Milestone: 7.6.1
Component: Compiler Version: 7.4.1
Keywords: Generics Cc: patrick@…, bgamari@…
Operating System: Unknown/Multiple Architecture: Unknown/Multiple
Type of failure: None/Unknown Test Case: generics/GEq1, generics/GenCanDoRep0
Blocked By: Blocking:
Related Tickets: Differential Rev(s):
Wiki Page:

Description

Currently DeriveGeneric doesn't handle data families correctly, so that the following module

{-# LANGUAGE TypeFamilies, DeriveGeneric #-}
module FamilyDerive where
import GHC.Generics

data family F a
data instance F Int = FInt deriving Generic

fails to compile, with error

/tmp/FamilyDerive.hs:6:15:
    Couldn't match type `Rep (F Int)' with `M1 t0 t1 (M1 t2 t3 U1)'
    The type variables `t0', `t1', `t2', `t3' are ambiguous
    Possible fix: add a type signature that fixes these type variable(s)
    Expected type: Rep (F Int) x
      Actual type: M1 t0 t1 (M1 t2 t3 U1) x
    In the pattern: M1 (M1 U1)
    In an equation for `to': to (M1 (M1 U1)) = FInt
    In the instance declaration for `Generic (F Int)'

It turns out to require only small changes to GHC to handle data families. I've attached patches.

Attachments (2)

0001-Make-DeriveGeneric-support-data-families.patch (3.0 KB) - added by reinerp 8 years ago.
Patch for ghc
0001-Test-DeriveGeneric-for-data-families.patch (3.6 KB) - added by reinerp 8 years ago.
Patch for testsuite

Download all attachments as: .zip

Change History (16)

Changed 8 years ago by reinerp

Patch for ghc

Changed 8 years ago by reinerp

Patch for testsuite

comment:1 Changed 8 years ago by reinerp

Status: newpatch

comment:2 Changed 8 years ago by dreixel

Owner: set to dreixel

Thanks for the patch! I'm just not entirely sure if this is "the right way" to support data families. For a data family

data family D a
data instance D Int  = DInt
data instance D Bool = DBool

your patch basically says that D Int is one datatype, and D Bool is another (unrelated) datatype. This might very well be the only thing we can do for data families; at least I cannot quickly come up with an idea of how to do it in any other way. But I would like to hear what other people think of this... maybe we should start a discussion on the generics/libraries mailing list?

comment:3 Changed 8 years ago by simonpj

difficulty: Unknown

Hmm. Yes, it pretty much is the case that (D Int) and (D Bool) are unrelated data types. I that's fair enough.

Simon

comment:4 Changed 7 years ago by parcs

Cc: patrick@… added

comment:5 Changed 7 years ago by bgamari

Cc: bgamari@… added

comment:6 Changed 7 years ago by bgamari

Any thoughts on how to move forward on this?

comment:7 in reply to:  6 Changed 7 years ago by dreixel

Replying to bgamari:

Any thoughts on how to move forward on this?

I don't think it'll be too hard; I've just been very busy with deadlines. Hope to have a look at it next week.

comment:8 Changed 7 years ago by simonpj

Here's the relevant thread on the libraries list: http://www.haskell.org/pipermail/libraries/2012-May/017815.html. Excerpts:

Reiner: I have tried using GHC's new generic deriving 2 to derive instances - this is almost possible, but is blocked by a GHC issue 3. IMHO generic deriving would be the best solution (once it works), because it works for product types as well as newtypes, and requires no extra GHC assistance or TH.

Ben: This will be quite nice and it sounds like it should cover nearly all of the cases I'm interested in. I'm not terribly familiar with generics support so I'm not sure whether this is possible or not, but it would be great if there were a way to specify whether an SoA or AoS representation is derived. This way one could write nearly cache-optimal code while keeping the mechanics of data layout nicely contained.

comment:9 Changed 7 years ago by pcapriotti

Milestone: 7.6.1

comment:10 Changed 7 years ago by jpm@…

commit 156ec95a8e92cc8314db134311d2fbb0269f0679

Author: Jose Pedro Magalhaes <jpm@cs.ox.ac.uk>
Date:   Thu Jun 21 12:23:01 2012 +0100

    Allow deriving Generic1
    
    This completes the support for generic programming introduced
    in GHC 7.2. Generic1 allows defining generic functions that
    operate on type containers, such as `fmap`, for instance.
    
    Along the way we have fixed #5936 and #5939, allowing
    deriving Generic/Generic1 for data families, and disallowing
    deriving Generic/Generic1 for instantiated types.
    
    Most of this patch is Nicolas Frisby's work.

 compiler/basicTypes/OccName.lhs      |    5 +-
 compiler/prelude/PrelNames.lhs       |   13 +-
 compiler/typecheck/TcDeriv.lhs       |  158 +++++++----
 compiler/typecheck/TcGenGenerics.lhs |  514 ++++++++++++++++++++++++++--------
 4 files changed, 521 insertions(+), 169 deletions(-)

comment:11 Changed 7 years ago by dreixel

Resolution: fixed
Status: patchclosed

Thanks, I have manually applied your patch, but forgot to acknowledge you in the commit, sorry about that :-/

comment:12 Changed 7 years ago by dreixel

Test Case: GEq1

comment:13 Changed 7 years ago by simonpj

Test Case: GEq1generics/GEq1, generics/GenCanDoRep0

Adding GenCanDoRep0 as a test for this too.

comment:14 Changed 3 years ago by RyanGlScott

Keywords: Generics added
Note: See TracTickets for help on using tickets.