[Haskell-cafe] Replace data constructors via meta programming

Vilem-Benjamin Liepelt vl81 at kent.ac.uk
Mon Feb 12 02:30:44 UTC 2018


I am looking for a solution to get rid of this silly boilerplate:

eval :: Ord var => Map var Bool -> Proposition var -> Bool
eval ctx prop = evalP $ fmap (ctx Map.!) prop
    evalP = \case
        Var b -> b
        Not q -> not $ evalP q
        And p q -> evalP p && evalP q
        Or p q -> evalP p || evalP q
        If p q -> evalP p ==> evalP q
        Iff p q -> evalP p == evalP q

What I would like to do in essence is to replace the data constructors like so:

-- Not valid Haskell!! Can't pattern match on constructor only...
magic = \case
    Var -> id
    Not -> not
    And -> (&&)
    Or -> (||)
    If -> (==>)
    Iff -> (==)

compile = transformAST magic $ fmap (\case 'P' -> False; 'Q' -> True)

>>> compile (Iff (Not (And (Var 'P') (Var 'Q'))) (Or (Not (Var 'P')) (Not (Var 'Q'))))
            ((==) (not ((&&) (id True) (id False))) ((||) (not (id True)) (not (id False))))

Note how the compiled expression exactly mirrors the AST, so there should be some meta programming technique for this.

Does anyone have an idea how I can achieve this?

The full source code is here: https://gist.github.com/vimuel/7dcb8a9f1d2b7b72f020d66ec4157d7b

I am happy to take any other comments relating to my code...


-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mail.haskell.org/pipermail/haskell-cafe/attachments/20180212/63d91c99/attachment.html>

More information about the Haskell-Cafe mailing list