Proposal: liftData for Template Haskell

Edward Z. Yang ezyang at
Tue May 5 16:18:16 UTC 2015

Hello Michael,

The Data instance for Map is a very interesting one indeed.  Honestly, I
really hate this instance, and I really hate generating a VarE, in part
because there is no guarantee that fromList is defined in the same
module as the type definition.

But it gives a valuable clue about how dataToQa: maybe it's wrong for us
to try to directly make names based on the Constr information that is
given to us: instead, the generate TH code should be a call to /gunfold/
(with TH lifting the Constr).  Of course, this would be even more
inefficient, but maybe the optimizer can figure it out.
Unfortunately, I don't actually know how to encode an arbitrary
constructor invocation indirected through Data.


Excerpts from Michael Sloan's message of 2015-04-18 12:50:39 -0700:
> +1 to liftData
> Removing 'Lift' altogether definitely isn't the way to go, though. As
> Richard points out, we want to be able to lift more than just ADTs.  Also
> ADTs which hide their implementation can have either opaque Data instances,
> no Data instance, or Data instances which involve using functions for
> constructors.
> An example of the latter is Data.Map.Map's Data instance, which uses
> 'fromList' as a constructor.  This results in $(dataToExpQ (\_ -> Nothing)
> (fromList [(1,2)])) causing the compiletime error "Illegal data constructor
> name: ‘fromList’".
> I think 'dataToExpQ' and related functions should be modified to handle
> this case.  It should be rather easy - if the constructor Name is
> lowercase, generate a 'VarE' instead of a 'ConE'.  I suppose this is a
> separate proposal, but it came up when thinking about this proposal.
> -Michael
> On Fri, Apr 17, 2015 at 4:21 AM, Edward Z. Yang <ezyang at> wrote:
> > I propose adding the following function to Language.Haskell.TH:
> >
> >     -- | 'liftData' is a variant of 'lift' in the 'Lift' type class which
> >     -- works for any type with a 'Data' instance.
> >     liftData :: Data a => a -> Q Exp
> >     liftData = dataToExpQ (const Nothing)
> >
> > I don't really know which submodule this should come from;
> > since it uses 'dataToExpQ', you might put it in Language.Haskell.TH.Quote
> > but arguably 'dataToExpQ' doesn't belong in this module either,
> > and it only lives there because it is a useful function for defining
> > quasiquoters and it was described in the quasiquoting paper.
> >
> > I might propose getting rid of the 'Lift' class entirely, but you
> > might prefer that class since it doesn't go through SYB (and have
> > the attendant slowdown).
> >
> > This mode of use of 'dataToExpQ' deserves more attention.
> >
> > Discussion period: 1 month
> >
> > Cheers,
> > Edward
> > _______________________________________________
> > Libraries mailing list
> > Libraries at
> >
> >

More information about the Libraries mailing list