Ralf Lammel wrote:
As Bulat points out, the GHC primitive dataToTag#
indeed nicely solves the problem. Ben, just for
completeness' sake; with SYB, you get such reflective
information too (and others):

shallowEq :: Data a => a -> a -> Bool
shallowEq x y = toConstr x == toConstr y

(dataToTag# returns Int, while toConstr comprises other things like the
constructor name.)


Ralf,
Yes, I ended up using the "propper" SYB approach instead, though I have noticed that the reflection data types Constr and DataRep make no mention of type variables or functions.

For example, this works fine:
> getTag (Just 5)           ==# getTag (Just{})
> getTag (Just (\x -> x))   ==# getTag (Just{})

But this does not
> toConstr (Just 5)         == toConstr (Just{})
    Ambiguous type variables.

> toConstr (Just (\x -> x)) == toConstr (Just{})
    No instance for Data (t -> t)

I appreciate the reasons why this is so, though I think it's interesting to see the practical consequences.

A toConstr version of shallowEq works ok so long as you provide a type signature to constrain both arguments to be the same type, and one of them is always fully constructed - which is fine for me at the moment.

Ben.


_______________________________________________
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe

Reply via email to