{-# LANGUAGE ExistentialQuantification, PatternGuards, Rank2Types #-}
module Lambdabot.Plugin.Haskell.Pl.Rules (RewriteRule(..), fire, rules) where
import Lambdabot.Plugin.Haskell.Pl.Common
import Lambdabot.Plugin.Haskell.Pl.RuleLib
import Lambdabot.Plugin.Haskell.Pl.Names
collapseLists :: Expr -> Maybe Expr
collapseLists :: Expr -> Maybe Expr
collapseLists (Var _ "++" `App` e1 :: Expr
e1 `App` e2 :: Expr
e2)
| (xs :: [Expr]
xs,x :: Expr
x) <- Expr -> ([Expr], Expr)
getList Expr
e1, Expr
xExpr -> Expr -> Bool
forall a. Eq a => a -> a -> Bool
==Expr
nil,
(ys :: [Expr]
ys,y :: Expr
y) <- Expr -> ([Expr], Expr)
getList Expr
e2, Expr
yExpr -> Expr -> Bool
forall a. Eq a => a -> a -> Bool
==Expr
nil = Expr -> Maybe Expr
forall a. a -> Maybe a
Just (Expr -> Maybe Expr) -> Expr -> Maybe Expr
forall a b. (a -> b) -> a -> b
$ [Expr] -> Expr
makeList ([Expr] -> Expr) -> [Expr] -> Expr
forall a b. (a -> b) -> a -> b
$ [Expr]
xs [Expr] -> [Expr] -> [Expr]
forall a. [a] -> [a] -> [a]
++ [Expr]
ys
collapseLists _ = Maybe Expr
forall a. Maybe a
Nothing
data Binary = forall a b c. (Read a, Show a, Read b, Show b, Read c, Show c) => BA (a -> b -> c)
evalBinary :: [(String, Binary)] -> Expr -> Maybe Expr
evalBinary :: [(String, Binary)] -> Expr -> Maybe Expr
evalBinary fs :: [(String, Binary)]
fs (Var _ f' :: String
f' `App` Var _ x' :: String
x' `App` Var _ y' :: String
y')
| Just (BA f :: a -> b -> c
f) <- String -> [(String, Binary)] -> Maybe Binary
forall a b. Eq a => a -> [(a, b)] -> Maybe b
lookup String
f' [(String, Binary)]
fs = (Fixity -> String -> Expr
Var Fixity
Pref (String -> Expr) -> (c -> String) -> c -> Expr
forall b c a. (b -> c) -> (a -> b) -> a -> c
. c -> String
forall a. Show a => a -> String
show) (c -> Expr) -> Maybe c -> Maybe Expr
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
`fmap` (a -> b -> c) -> Maybe a -> Maybe b -> Maybe c
forall (m :: * -> *) a1 a2 r.
Monad m =>
(a1 -> a2 -> r) -> m a1 -> m a2 -> m r
liftM2 a -> b -> c
f (String -> Maybe a
forall a (m :: * -> *). (Read a, Alternative m) => String -> m a
readM String
x') (String -> Maybe b
forall a (m :: * -> *). (Read a, Alternative m) => String -> m a
readM String
y')
evalBinary _ _ = Maybe Expr
forall a. Maybe a
Nothing
data Unary = forall a b. (Read a, Show a, Read b, Show b) => UA (a -> b)
evalUnary :: [(String, Unary)] -> Expr -> Maybe Expr
evalUnary :: [(String, Unary)] -> Expr -> Maybe Expr
evalUnary fs :: [(String, Unary)]
fs (Var _ f' :: String
f' `App` Var _ x' :: String
x')
| Just (UA f :: a -> b
f) <- String -> [(String, Unary)] -> Maybe Unary
forall a b. Eq a => a -> [(a, b)] -> Maybe b
lookup String
f' [(String, Unary)]
fs = (Fixity -> String -> Expr
Var Fixity
Pref (String -> Expr) -> (a -> String) -> a -> Expr
forall b c a. (b -> c) -> (a -> b) -> a -> c
. b -> String
forall a. Show a => a -> String
show (b -> String) -> (a -> b) -> a -> String
forall b c a. (b -> c) -> (a -> b) -> a -> c
. a -> b
f) (a -> Expr) -> Maybe a -> Maybe Expr
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
`fmap` String -> Maybe a
forall a (m :: * -> *). (Read a, Alternative m) => String -> m a
readM String
x'
evalUnary _ _ = Maybe Expr
forall a. Maybe a
Nothing
assocR, assocL, assoc :: [String] -> Expr -> Maybe Expr
assocR :: [String] -> Expr -> Maybe Expr
assocR ops :: [String]
ops (Var f1 :: Fixity
f1 op1 :: String
op1 `App` (Var f2 :: Fixity
f2 op2 :: String
op2 `App` e1 :: Expr
e1 `App` e2 :: Expr
e2) `App` e3 :: Expr
e3)
| String
op1 String -> String -> Bool
forall a. Eq a => a -> a -> Bool
== String
op2 Bool -> Bool -> Bool
&& String
op1 String -> [String] -> Bool
forall (t :: * -> *) a. (Foldable t, Eq a) => a -> t a -> Bool
`elem` [String]
ops
= Expr -> Maybe Expr
forall a. a -> Maybe a
Just (Fixity -> String -> Expr
Var Fixity
f1 String
op1 Expr -> Expr -> Expr
`App` Expr
e1 Expr -> Expr -> Expr
`App` (Fixity -> String -> Expr
Var Fixity
f2 String
op2 Expr -> Expr -> Expr
`App` Expr
e2 Expr -> Expr -> Expr
`App` Expr
e3))
assocR _ _ = Maybe Expr
forall a. Maybe a
Nothing
assocL :: [String] -> Expr -> Maybe Expr
assocL ops :: [String]
ops (Var f1 :: Fixity
f1 op1 :: String
op1 `App` e1 :: Expr
e1 `App` (Var f2 :: Fixity
f2 op2 :: String
op2 `App` e2 :: Expr
e2 `App` e3 :: Expr
e3))
| String
op1 String -> String -> Bool
forall a. Eq a => a -> a -> Bool
== String
op2 Bool -> Bool -> Bool
&& String
op1 String -> [String] -> Bool
forall (t :: * -> *) a. (Foldable t, Eq a) => a -> t a -> Bool
`elem` [String]
ops
= Expr -> Maybe Expr
forall a. a -> Maybe a
Just (Fixity -> String -> Expr
Var Fixity
f1 String
op1 Expr -> Expr -> Expr
`App` (Fixity -> String -> Expr
Var Fixity
f2 String
op2 Expr -> Expr -> Expr
`App` Expr
e1 Expr -> Expr -> Expr
`App` Expr
e2) Expr -> Expr -> Expr
`App` Expr
e3)
assocL _ _ = Maybe Expr
forall a. Maybe a
Nothing
assoc :: [String] -> Expr -> Maybe Expr
assoc ops :: [String]
ops (Var _ "." `App` (Var f1 :: Fixity
f1 op1 :: String
op1 `App` e1 :: Expr
e1) `App` (Var f2 :: Fixity
f2 op2 :: String
op2 `App` e2 :: Expr
e2))
| String
op1 String -> String -> Bool
forall a. Eq a => a -> a -> Bool
== String
op2 Bool -> Bool -> Bool
&& String
op1 String -> [String] -> Bool
forall (t :: * -> *) a. (Foldable t, Eq a) => a -> t a -> Bool
`elem` [String]
ops
= Expr -> Maybe Expr
forall a. a -> Maybe a
Just (Fixity -> String -> Expr
Var Fixity
f1 String
op1 Expr -> Expr -> Expr
`App` (Fixity -> String -> Expr
Var Fixity
f2 String
op2 Expr -> Expr -> Expr
`App` Expr
e1 Expr -> Expr -> Expr
`App` Expr
e2))
assoc _ _ = Maybe Expr
forall a. Maybe a
Nothing
commutative :: [String] -> Expr -> Maybe Expr
commutative :: [String] -> Expr -> Maybe Expr
commutative ops :: [String]
ops (Var f :: Fixity
f op :: String
op `App` e1 :: Expr
e1 `App` e2 :: Expr
e2)
| String
op String -> [String] -> Bool
forall (t :: * -> *) a. (Foldable t, Eq a) => a -> t a -> Bool
`elem` [String]
ops = Expr -> Maybe Expr
forall a. a -> Maybe a
Just (Fixity -> String -> Expr
Var Fixity
f String
op Expr -> Expr -> Expr
`App` Expr
e2 Expr -> Expr -> Expr
`App` Expr
e1)
commutative ops :: [String]
ops (Var _ "flip" `App` e :: Expr
e@(Var _ op :: String
op)) | String
op String -> [String] -> Bool
forall (t :: * -> *) a. (Foldable t, Eq a) => a -> t a -> Bool
`elem` [String]
ops = Expr -> Maybe Expr
forall a. a -> Maybe a
Just Expr
e
commutative _ _ = Maybe Expr
forall a. Maybe a
Nothing
{-# INLINE simplifies #-}
simplifies :: RewriteRule
simplifies :: RewriteRule
simplifies = [RewriteRule] -> RewriteRule
Or [
(MExpr -> MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr0 (\f :: MExpr
f g :: MExpr
g x :: MExpr
x -> (MExpr
f MExpr -> MExpr -> MExpr
`c` MExpr
g) MExpr -> MExpr -> MExpr
`a` MExpr
x)
(\f :: MExpr
f g :: MExpr
g x :: MExpr
x -> MExpr
f MExpr -> MExpr -> MExpr
`a` (MExpr
g MExpr -> MExpr -> MExpr
`a` MExpr
x)),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr0 (\x :: MExpr
x -> MExpr
idE MExpr -> MExpr -> MExpr
`a` MExpr
x)
(\x :: MExpr
x -> MExpr
x),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\x :: MExpr
x -> MExpr
flipE MExpr -> MExpr -> MExpr
`a` (MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
x))
(\x :: MExpr
x -> MExpr
x),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr0 (\f :: MExpr
f x :: MExpr
x -> (MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
idE MExpr -> MExpr -> MExpr
`a` MExpr
x) MExpr -> MExpr -> MExpr
`c` MExpr
f)
(\f :: MExpr
f x :: MExpr
x -> MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
x),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr0 (\f :: MExpr
f -> MExpr
idE MExpr -> MExpr -> MExpr
`c` MExpr
f)
(\f :: MExpr
f -> MExpr
f),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr0 (\f :: MExpr
f -> MExpr
f MExpr -> MExpr -> MExpr
`c` MExpr
idE)
(\f :: MExpr
f -> MExpr
f),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr0 (\x :: MExpr
x y :: MExpr
y -> MExpr
constE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
y)
(\x :: MExpr
x _ -> MExpr
x),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\x :: MExpr
x -> MExpr
notE MExpr -> MExpr -> MExpr
`a` (MExpr
notE MExpr -> MExpr -> MExpr
`a` MExpr
x))
(\x :: MExpr
x -> MExpr
x),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\x :: MExpr
x y :: MExpr
y -> MExpr
fstE MExpr -> MExpr -> MExpr
`a` (MExpr
commaE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
y))
(\x :: MExpr
x _ -> MExpr
x),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\x :: MExpr
x y :: MExpr
y -> MExpr
sndE MExpr -> MExpr -> MExpr
`a` (MExpr
commaE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
y))
(\_ y :: MExpr
y -> MExpr
y),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\x :: MExpr
x xs :: MExpr
xs -> MExpr
headE MExpr -> MExpr -> MExpr
`a` (MExpr
consE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
xs))
(\x :: MExpr
x _ -> MExpr
x),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\x :: MExpr
x xs :: MExpr
xs -> MExpr
tailE MExpr -> MExpr -> MExpr
`a` (MExpr
consE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
xs))
(\_ xs :: MExpr
xs -> MExpr
xs),
(MExpr -> MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr1 (\f :: MExpr
f x :: MExpr
x y :: MExpr
y -> MExpr
uncurryE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` (MExpr
commaE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
y))
(\f :: MExpr
f x :: MExpr
x y :: MExpr
y -> MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
y),
MExpr -> MExpr -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (MExpr
uncurryE MExpr -> MExpr -> MExpr
`a` MExpr
commaE)
(MExpr
idE),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr1 (\f :: MExpr
f g :: MExpr
g -> (MExpr
uncurryE MExpr -> MExpr -> MExpr
`a` MExpr
f) MExpr -> MExpr -> MExpr
`c` (MExpr
sE MExpr -> MExpr -> MExpr
`a` MExpr
commaE MExpr -> MExpr -> MExpr
`a` MExpr
g))
(\f :: MExpr
f g :: MExpr
g -> MExpr
sE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
g),
MExpr -> MExpr -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (MExpr
curryE MExpr -> MExpr -> MExpr
`a` MExpr
fstE) (MExpr
constE),
MExpr -> MExpr -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (MExpr
curryE MExpr -> MExpr -> MExpr
`a` MExpr
sndE) (MExpr
constE MExpr -> MExpr -> MExpr
`a` MExpr
idE),
(MExpr -> MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr0 (\f :: MExpr
f g :: MExpr
g x :: MExpr
x -> MExpr
sE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
g MExpr -> MExpr -> MExpr
`a` MExpr
x)
(\f :: MExpr
f g :: MExpr
g x :: MExpr
x -> MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` (MExpr
g MExpr -> MExpr -> MExpr
`a` MExpr
x)),
(MExpr -> MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr0 (\f :: MExpr
f x :: MExpr
x y :: MExpr
y -> MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
y)
(\f :: MExpr
f x :: MExpr
x y :: MExpr
y -> MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
y MExpr -> MExpr -> MExpr
`a` MExpr
x),
MExpr -> MExpr -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr0 (MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
extE)
MExpr
bindE,
MExpr -> MExpr -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (MExpr
fmapE MExpr -> MExpr -> MExpr
`a` MExpr
idE)
(MExpr
idE),
MExpr -> MExpr -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (MExpr
mapE MExpr -> MExpr -> MExpr
`a` MExpr
idE)
(MExpr
idE),
(MExpr -> MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr0 (\f :: MExpr
f g :: MExpr
g h :: MExpr
h -> (MExpr
f MExpr -> MExpr -> MExpr
`c` MExpr
g) MExpr -> MExpr -> MExpr
`c` MExpr
h)
(\f :: MExpr
f g :: MExpr
g h :: MExpr
h -> MExpr
f MExpr -> MExpr -> MExpr
`c` (MExpr
g MExpr -> MExpr -> MExpr
`c` MExpr
h)),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr0 (\f :: MExpr
f g :: MExpr
g -> MExpr
fmapE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`c` MExpr
fmapE MExpr -> MExpr -> MExpr
`a` MExpr
g)
(\f :: MExpr
f g :: MExpr
g -> MExpr
fmapE MExpr -> MExpr -> MExpr
`a` (MExpr
f MExpr -> MExpr -> MExpr
`c` MExpr
g)),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr0 (\f :: MExpr
f g :: MExpr
g -> MExpr
mapE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`c` MExpr
mapE MExpr -> MExpr -> MExpr
`a` MExpr
g)
(\f :: MExpr
f g :: MExpr
g -> MExpr
mapE MExpr -> MExpr -> MExpr
`a` (MExpr
f MExpr -> MExpr -> MExpr
`c` MExpr
g))
]
onceRewrites :: RewriteRule
onceRewrites :: RewriteRule
onceRewrites = RewriteRule -> RewriteRule
Hard (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$ [RewriteRule] -> RewriteRule
Or [
MExpr -> MExpr -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr0 (MExpr
dollarE)
MExpr
idE,
MExpr -> MExpr -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr MExpr
concatMapE MExpr
extE,
MExpr -> MExpr -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr MExpr
concatE MExpr
joinE,
MExpr -> MExpr -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr MExpr
liftME MExpr
fmapE,
MExpr -> MExpr -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr MExpr
mapE MExpr
fmapE,
MExpr -> MExpr -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr MExpr
subtractE
(MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
minusE)
]
rules :: RewriteRule
rules :: RewriteRule
rules = [RewriteRule] -> RewriteRule
Or [
RewriteRule -> RewriteRule
Hard (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$
(MExpr -> MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f g :: MExpr
g x :: MExpr
x -> MExpr
f MExpr -> MExpr -> MExpr
`a` (MExpr
g MExpr -> MExpr -> MExpr
`a` MExpr
x))
(\f :: MExpr
f g :: MExpr
g x :: MExpr
x -> (MExpr
f MExpr -> MExpr -> MExpr
`c` MExpr
g) MExpr -> MExpr -> MExpr
`a` MExpr
x),
RewriteRule -> RewriteRule
Hard (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$
MExpr -> MExpr -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr MExpr
bindE
(MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
extE),
MExpr -> MExpr -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (MExpr
compE MExpr -> MExpr -> MExpr
`a` MExpr
idE)
MExpr
idE,
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\x :: MExpr
x -> MExpr
appendE MExpr -> MExpr -> MExpr
`a` (MExpr
consE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
nilE))
(\x :: MExpr
x -> MExpr
consE MExpr -> MExpr -> MExpr
`a` MExpr
x),
MExpr -> MExpr -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (MExpr
extE MExpr -> MExpr -> MExpr
`a` MExpr
returnE)
MExpr
idE,
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f x :: MExpr
x -> MExpr
extE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` (MExpr
returnE MExpr -> MExpr -> MExpr
`a` MExpr
x))
(\f :: MExpr
f x :: MExpr
x -> MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
x),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f g :: MExpr
g -> MExpr
extE MExpr -> MExpr -> MExpr
`a` ((MExpr
extE MExpr -> MExpr -> MExpr
`a` MExpr
f) MExpr -> MExpr -> MExpr
`c` MExpr
g))
(\f :: MExpr
f g :: MExpr
g -> (MExpr
extE MExpr -> MExpr -> MExpr
`a` MExpr
f) MExpr -> MExpr -> MExpr
`c` (MExpr
extE MExpr -> MExpr -> MExpr
`a` MExpr
g)),
RewriteRule -> RewriteRule
Hard (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f g :: MExpr
g -> MExpr
flipE MExpr -> MExpr -> MExpr
`a` (MExpr
f MExpr -> MExpr -> MExpr
`c` MExpr
g))
(\f :: MExpr
f g :: MExpr
g -> (MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
compE MExpr -> MExpr -> MExpr
`a` MExpr
g) MExpr -> MExpr -> MExpr
`c` (MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
f)),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f -> (MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
compE MExpr -> MExpr -> MExpr
`a` MExpr
f) MExpr -> MExpr -> MExpr
`c` (MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
idE))
(\f :: MExpr
f -> MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
f),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f -> (MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
compE MExpr -> MExpr -> MExpr
`a` MExpr
f) MExpr -> MExpr -> MExpr
`c` (MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
flipE))
(\f :: MExpr
f -> MExpr
flipE MExpr -> MExpr -> MExpr
`a` (MExpr
flipE MExpr -> MExpr -> MExpr
`c` MExpr
f)),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr1 (\f :: MExpr
f g :: MExpr
g -> MExpr
flipE MExpr -> MExpr -> MExpr
`a` (MExpr
flipE MExpr -> MExpr -> MExpr
`a` (MExpr
flipE MExpr -> MExpr -> MExpr
`c` MExpr
f) MExpr -> MExpr -> MExpr
`a` MExpr
g))
(\f :: MExpr
f g :: MExpr
g -> MExpr
flipE MExpr -> MExpr -> MExpr
`a` (MExpr
flipE MExpr -> MExpr -> MExpr
`c` MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
f) MExpr -> MExpr -> MExpr
`a` MExpr
g),
MExpr -> MExpr -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
compE MExpr -> MExpr -> MExpr
`a` MExpr
idE)
MExpr
idE,
MExpr -> MExpr -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (MExpr
compE MExpr -> MExpr -> MExpr
`c` (MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
idE))
(MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
flipE),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\x :: MExpr
x y :: MExpr
y -> MExpr
sE MExpr -> MExpr -> MExpr
`a` MExpr
constE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
y)
(\_ y :: MExpr
y -> MExpr
y),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr1 (\f :: MExpr
f g :: MExpr
g -> MExpr
sE MExpr -> MExpr -> MExpr
`a` (MExpr
constE MExpr -> MExpr -> MExpr
`c` MExpr
f) MExpr -> MExpr -> MExpr
`a` MExpr
g)
(\f :: MExpr
f _ -> MExpr
f),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f -> MExpr
sE MExpr -> MExpr -> MExpr
`a` (MExpr
constE MExpr -> MExpr -> MExpr
`a` MExpr
f))
(\f :: MExpr
f -> MExpr
compE MExpr -> MExpr -> MExpr
`a` MExpr
f),
(MExpr -> MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f g :: MExpr
g h :: MExpr
h -> (MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
sE MExpr -> MExpr -> MExpr
`a` MExpr
f) MExpr -> MExpr -> MExpr
`c` (MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
compE MExpr -> MExpr -> MExpr
`a` MExpr
g) MExpr -> MExpr -> MExpr
`c` MExpr
constE MExpr -> MExpr -> MExpr
`c` MExpr
h)
(\f :: MExpr
f _ h :: MExpr
h -> (MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
compE MExpr -> MExpr -> MExpr
`a` MExpr
f) MExpr -> MExpr -> MExpr
`c` MExpr
h),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f -> MExpr
sE MExpr -> MExpr -> MExpr
`a` (MExpr
f MExpr -> MExpr -> MExpr
`c` MExpr
fstE) MExpr -> MExpr -> MExpr
`a` MExpr
sndE)
(\f :: MExpr
f -> MExpr
uncurryE MExpr -> MExpr -> MExpr
`a` MExpr
f),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\x :: MExpr
x -> MExpr
fstE MExpr -> MExpr -> MExpr
`a` (MExpr
joinE MExpr -> MExpr -> MExpr
`a` MExpr
commaE MExpr -> MExpr -> MExpr
`a` MExpr
x))
(\x :: MExpr
x -> MExpr
x),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\x :: MExpr
x -> MExpr
sndE MExpr -> MExpr -> MExpr
`a` (MExpr
joinE MExpr -> MExpr -> MExpr
`a` MExpr
commaE MExpr -> MExpr -> MExpr
`a` MExpr
x))
(\x :: MExpr
x -> MExpr
x),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f -> MExpr
curryE MExpr -> MExpr -> MExpr
`a` (MExpr
uncurryE MExpr -> MExpr -> MExpr
`a` MExpr
f))
(\f :: MExpr
f -> MExpr
f),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f -> MExpr
uncurryE MExpr -> MExpr -> MExpr
`a` (MExpr
curryE MExpr -> MExpr -> MExpr
`a` MExpr
f))
(\f :: MExpr
f -> MExpr
f),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f -> (MExpr
constE MExpr -> MExpr -> MExpr
`a` MExpr
idE) MExpr -> MExpr -> MExpr
`c` MExpr
f)
(\_ -> MExpr
constE MExpr -> MExpr -> MExpr
`a` MExpr
idE),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\x :: MExpr
x f :: MExpr
f -> MExpr
constE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`c` MExpr
f)
(\x :: MExpr
x _ -> MExpr
constE MExpr -> MExpr -> MExpr
`a` MExpr
x),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f -> (MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
compE MExpr -> MExpr -> MExpr
`a` MExpr
f) MExpr -> MExpr -> MExpr
`c` MExpr
constE)
(\_ -> MExpr
constE),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f g :: MExpr
g -> (MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
compE MExpr -> MExpr -> MExpr
`a` MExpr
f) MExpr -> MExpr -> MExpr
`c` MExpr
constE MExpr -> MExpr -> MExpr
`c` MExpr
g)
(\_ g :: MExpr
g -> MExpr
constE MExpr -> MExpr -> MExpr
`c` MExpr
g),
RewriteRule -> RewriteRule
Hard (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr0 (\f :: MExpr
f -> MExpr
fixE MExpr -> MExpr -> MExpr
`a` MExpr
f)
(\f :: MExpr
f -> MExpr
f MExpr -> MExpr -> MExpr
`a` (MExpr
fixE MExpr -> MExpr -> MExpr
`a` MExpr
f)),
RewriteRule -> RewriteRule
Hard (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr0 (\f :: MExpr
f -> MExpr
f MExpr -> MExpr -> MExpr
`a` (MExpr
fixE MExpr -> MExpr -> MExpr
`a` MExpr
f))
(\f :: MExpr
f -> MExpr
fixE MExpr -> MExpr -> MExpr
`a` MExpr
f),
RewriteRule -> RewriteRule
Hard (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr0 (\f :: MExpr
f -> MExpr
fixE MExpr -> MExpr -> MExpr
`a` MExpr
f)
(\f :: MExpr
f -> MExpr
f MExpr -> MExpr -> MExpr
`a` (MExpr
f MExpr -> MExpr -> MExpr
`a` (MExpr
fixE MExpr -> MExpr -> MExpr
`a` MExpr
f))),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f -> MExpr
fixE MExpr -> MExpr -> MExpr
`a` (MExpr
constE MExpr -> MExpr -> MExpr
`a` MExpr
f))
(\f :: MExpr
f -> MExpr
f),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\x :: MExpr
x -> MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
constE MExpr -> MExpr -> MExpr
`a` MExpr
x)
(\_ -> MExpr
idE),
RewriteRule -> RewriteRule
Hard (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f -> MExpr
constE MExpr -> MExpr -> MExpr
`c` MExpr
f)
(\f :: MExpr
f -> MExpr
flipE MExpr -> MExpr -> MExpr
`a` (MExpr
constE MExpr -> MExpr -> MExpr
`a` MExpr
f)),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr2 (\x :: MExpr
x y :: MExpr
y -> MExpr
notE MExpr -> MExpr -> MExpr
`a` (MExpr
equalsE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
y))
(\x :: MExpr
x y :: MExpr
y -> MExpr
nequalsE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
y),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr2 (\x :: MExpr
x y :: MExpr
y -> MExpr
notE MExpr -> MExpr -> MExpr
`a` (MExpr
nequalsE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
y))
(\x :: MExpr
x y :: MExpr
y -> MExpr
equalsE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
y),
RewriteRule -> RewriteRule -> RewriteRule
If ([RewriteRule] -> RewriteRule
Or [MExpr -> MExpr -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr MExpr
plusE MExpr
plusE, MExpr -> MExpr -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr MExpr
minusE MExpr
minusE, MExpr -> MExpr -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr MExpr
multE MExpr
multE]) (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$ RewriteRule -> RewriteRule
down (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$ [RewriteRule] -> RewriteRule
Or [
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\x :: MExpr
x -> MExpr
plusE MExpr -> MExpr -> MExpr
`a` MExpr
zeroE MExpr -> MExpr -> MExpr
`a` MExpr
x)
(\x :: MExpr
x -> MExpr
x),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\x :: MExpr
x -> MExpr
multE MExpr -> MExpr -> MExpr
`a` MExpr
zeroE MExpr -> MExpr -> MExpr
`a` MExpr
x)
(\_ -> MExpr
zeroE),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\x :: MExpr
x -> MExpr
multE MExpr -> MExpr -> MExpr
`a` MExpr
oneE MExpr -> MExpr -> MExpr
`a` MExpr
x)
(\x :: MExpr
x -> MExpr
x),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\x :: MExpr
x -> MExpr
minusE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
x)
(\_ -> MExpr
zeroE),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\y :: MExpr
y x :: MExpr
x -> MExpr
plusE MExpr -> MExpr -> MExpr
`a` (MExpr
minusE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
y) MExpr -> MExpr -> MExpr
`a` MExpr
y)
(\_ x :: MExpr
x -> MExpr
x),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\y :: MExpr
y x :: MExpr
x -> MExpr
minusE MExpr -> MExpr -> MExpr
`a` (MExpr
plusE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
y) MExpr -> MExpr -> MExpr
`a` MExpr
y)
(\_ x :: MExpr
x -> MExpr
x),
(MExpr -> MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\x :: MExpr
x y :: MExpr
y z :: MExpr
z -> MExpr
plusE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` (MExpr
minusE MExpr -> MExpr -> MExpr
`a` MExpr
y MExpr -> MExpr -> MExpr
`a` MExpr
z))
(\x :: MExpr
x y :: MExpr
y z :: MExpr
z -> MExpr
minusE MExpr -> MExpr -> MExpr
`a` (MExpr
plusE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
y) MExpr -> MExpr -> MExpr
`a` MExpr
z),
(MExpr -> MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\x :: MExpr
x y :: MExpr
y z :: MExpr
z -> MExpr
minusE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` (MExpr
plusE MExpr -> MExpr -> MExpr
`a` MExpr
y MExpr -> MExpr -> MExpr
`a` MExpr
z))
(\x :: MExpr
x y :: MExpr
y z :: MExpr
z -> MExpr
minusE MExpr -> MExpr -> MExpr
`a` (MExpr
minusE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
y) MExpr -> MExpr -> MExpr
`a` MExpr
z),
(MExpr -> MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\x :: MExpr
x y :: MExpr
y z :: MExpr
z -> MExpr
minusE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` (MExpr
minusE MExpr -> MExpr -> MExpr
`a` MExpr
y MExpr -> MExpr -> MExpr
`a` MExpr
z))
(\x :: MExpr
x y :: MExpr
y z :: MExpr
z -> MExpr
minusE MExpr -> MExpr -> MExpr
`a` (MExpr
plusE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
y) MExpr -> MExpr -> MExpr
`a` MExpr
z)
],
RewriteRule -> RewriteRule
Hard RewriteRule
onceRewrites,
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f x :: MExpr
x -> MExpr
joinE MExpr -> MExpr -> MExpr
`a` (MExpr
fmapE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
x))
(\f :: MExpr
f x :: MExpr
x -> MExpr
extE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
x),
MExpr -> MExpr -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (MExpr
extE MExpr -> MExpr -> MExpr
`a` MExpr
idE) MExpr
joinE,
RewriteRule -> RewriteRule
Hard (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$
MExpr -> MExpr -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr MExpr
joinE (MExpr
extE MExpr -> MExpr -> MExpr
`a` MExpr
idE),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\x :: MExpr
x -> MExpr
joinE MExpr -> MExpr -> MExpr
`a` (MExpr
returnE MExpr -> MExpr -> MExpr
`a` MExpr
x))
(\x :: MExpr
x -> MExpr
x),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f m :: MExpr
m -> MExpr
extE MExpr -> MExpr -> MExpr
`a` (MExpr
returnE MExpr -> MExpr -> MExpr
`c` MExpr
f) MExpr -> MExpr -> MExpr
`a` MExpr
m)
(\f :: MExpr
f m :: MExpr
m -> MExpr
fmapIE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
m),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f x :: MExpr
x -> MExpr
bindE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`c` (MExpr
compE MExpr -> MExpr -> MExpr
`a` MExpr
returnE) MExpr -> MExpr -> MExpr
`c` MExpr
f)
(\f :: MExpr
f x :: MExpr
x -> MExpr
flipE MExpr -> MExpr -> MExpr
`a` (MExpr
fmapIE MExpr -> MExpr -> MExpr
`c` MExpr
f) MExpr -> MExpr -> MExpr
`a` MExpr
x),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f -> MExpr
bindE MExpr -> MExpr -> MExpr
`a` (MExpr
returnE MExpr -> MExpr -> MExpr
`a` MExpr
f))
(\f :: MExpr
f -> MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
idE MExpr -> MExpr -> MExpr
`a` MExpr
f),
RewriteRule -> RewriteRule
Hard (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f x :: MExpr
x -> MExpr
liftM2E MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
x)
(\f :: MExpr
f x :: MExpr
x -> MExpr
apE MExpr -> MExpr -> MExpr
`a` (MExpr
fmapIE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
x)),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f x :: MExpr
x -> MExpr
liftM2E MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` (MExpr
returnE MExpr -> MExpr -> MExpr
`a` MExpr
x))
(\f :: MExpr
f x :: MExpr
x -> MExpr
fmapIE MExpr -> MExpr -> MExpr
`a` (MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
x)),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f x :: MExpr
x -> MExpr
fmapE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` (MExpr
returnE MExpr -> MExpr -> MExpr
`a` MExpr
x))
(\f :: MExpr
f x :: MExpr
x -> MExpr
returnE MExpr -> MExpr -> MExpr
`a` (MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
x)),
RewriteRule -> RewriteRule
Hard (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f -> MExpr
extE MExpr -> MExpr -> MExpr
`c` MExpr
flipE MExpr -> MExpr -> MExpr
`a` (MExpr
fmapE MExpr -> MExpr -> MExpr
`c` MExpr
f))
(\f :: MExpr
f -> MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
liftM2E MExpr -> MExpr -> MExpr
`a` MExpr
f),
RewriteRule -> RewriteRule
Hard (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$
MExpr -> MExpr -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr MExpr
compE MExpr
fmapE,
RewriteRule -> RewriteRule
Hard (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$
(MExpr -> MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f xs :: MExpr
xs ys :: MExpr
ys -> MExpr
mapE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` (MExpr
zipE MExpr -> MExpr -> MExpr
`a` MExpr
xs MExpr -> MExpr -> MExpr
`a` MExpr
ys))
(\f :: MExpr
f xs :: MExpr
xs ys :: MExpr
ys -> MExpr
zipWithE MExpr -> MExpr -> MExpr
`a` (MExpr
curryE MExpr -> MExpr -> MExpr
`a` MExpr
f) MExpr -> MExpr -> MExpr
`a` MExpr
xs MExpr -> MExpr -> MExpr
`a` MExpr
ys),
MExpr -> MExpr -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (MExpr
zipWithE MExpr -> MExpr -> MExpr
`a` MExpr
commaE) MExpr
zipE,
RewriteRule -> RewriteRule
Hard (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f -> MExpr
allE MExpr -> MExpr -> MExpr
`a` MExpr
f)
(\f :: MExpr
f -> MExpr
andE MExpr -> MExpr -> MExpr
`c` MExpr
mapE MExpr -> MExpr -> MExpr
`a` MExpr
f),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f -> MExpr
andE MExpr -> MExpr -> MExpr
`c` MExpr
mapE MExpr -> MExpr -> MExpr
`a` MExpr
f)
(\f :: MExpr
f -> MExpr
allE MExpr -> MExpr -> MExpr
`a` MExpr
f),
RewriteRule -> RewriteRule
Hard (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f -> MExpr
anyE MExpr -> MExpr -> MExpr
`a` MExpr
f)
(\f :: MExpr
f -> MExpr
orE MExpr -> MExpr -> MExpr
`c` MExpr
mapE MExpr -> MExpr -> MExpr
`a` MExpr
f),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f -> MExpr
orE MExpr -> MExpr -> MExpr
`c` MExpr
mapE MExpr -> MExpr -> MExpr
`a` MExpr
f)
(\f :: MExpr
f -> MExpr
anyE MExpr -> MExpr -> MExpr
`a` MExpr
f),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f x :: MExpr
x -> MExpr
apE MExpr -> MExpr -> MExpr
`a` (MExpr
returnE MExpr -> MExpr -> MExpr
`a` MExpr
f) MExpr -> MExpr -> MExpr
`a` MExpr
x)
(\f :: MExpr
f x :: MExpr
x -> MExpr
fmapIE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
x),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f x :: MExpr
x -> MExpr
apE MExpr -> MExpr -> MExpr
`a` (MExpr
fmapIE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
x))
(\f :: MExpr
f x :: MExpr
x -> MExpr
liftM2E MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
x),
RewriteRule -> RewriteRule
Hard (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f x :: MExpr
x -> MExpr
apE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
x)
(\f :: MExpr
f x :: MExpr
x -> MExpr
extE MExpr -> MExpr -> MExpr
`a` (MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
fmapIE MExpr -> MExpr -> MExpr
`a` MExpr
x) MExpr -> MExpr -> MExpr
`a` MExpr
f),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f x :: MExpr
x -> MExpr
extE MExpr -> MExpr -> MExpr
`a` (MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
fmapIE MExpr -> MExpr -> MExpr
`a` MExpr
x) MExpr -> MExpr -> MExpr
`a` MExpr
f)
(\f :: MExpr
f x :: MExpr
x -> MExpr
apE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
x),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f x :: MExpr
x -> MExpr
bindE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`c` MExpr
flipE MExpr -> MExpr -> MExpr
`a` (MExpr
fmapE MExpr -> MExpr -> MExpr
`c` MExpr
f))
(\f :: MExpr
f x :: MExpr
x -> MExpr
liftM2E MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
x),
(MExpr -> MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr0 (\f :: MExpr
f m :: MExpr
m x :: MExpr
x -> MExpr
extE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
m MExpr -> MExpr -> MExpr
`a` MExpr
x)
(\f :: MExpr
f m :: MExpr
m x :: MExpr
x -> MExpr
f MExpr -> MExpr -> MExpr
`a` (MExpr
m MExpr -> MExpr -> MExpr
`a` MExpr
x) MExpr -> MExpr -> MExpr
`a` MExpr
x),
(MExpr -> MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr0 (\f :: MExpr
f g :: MExpr
g x :: MExpr
x -> MExpr
fmapE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
g MExpr -> MExpr -> MExpr
`a` MExpr
x)
(\f :: MExpr
f g :: MExpr
g x :: MExpr
x -> MExpr
f MExpr -> MExpr -> MExpr
`a` (MExpr
g MExpr -> MExpr -> MExpr
`a` MExpr
x)),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\y :: MExpr
y x :: MExpr
x -> MExpr
returnE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
y)
(\y :: MExpr
y _ -> MExpr
y),
(MExpr -> MExpr -> MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr0 (\f :: MExpr
f g :: MExpr
g h :: MExpr
h x :: MExpr
x -> MExpr
liftM2E MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
g MExpr -> MExpr -> MExpr
`a` MExpr
h MExpr -> MExpr -> MExpr
`a` MExpr
x)
(\f :: MExpr
f g :: MExpr
g h :: MExpr
h x :: MExpr
x -> MExpr
f MExpr -> MExpr -> MExpr
`a` (MExpr
g MExpr -> MExpr -> MExpr
`a` MExpr
x) MExpr -> MExpr -> MExpr
`a` (MExpr
h MExpr -> MExpr -> MExpr
`a` MExpr
x)),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f -> MExpr
apE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
idE)
(\f :: MExpr
f -> MExpr
joinE MExpr -> MExpr -> MExpr
`a` MExpr
f),
RewriteRule -> RewriteRule
Hard (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\q :: MExpr
q p :: MExpr
p -> MExpr
extE MExpr -> MExpr -> MExpr
`a` (MExpr
constE MExpr -> MExpr -> MExpr
`a` MExpr
q) MExpr -> MExpr -> MExpr
`a` MExpr
p)
(\q :: MExpr
q p :: MExpr
p -> MExpr
seqME MExpr -> MExpr -> MExpr
`a` MExpr
p MExpr -> MExpr -> MExpr
`a` MExpr
q),
RewriteRule -> RewriteRule
Hard (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\p :: MExpr
p q :: MExpr
q -> MExpr
seqME MExpr -> MExpr -> MExpr
`a` MExpr
p MExpr -> MExpr -> MExpr
`a` MExpr
q)
(\p :: MExpr
p q :: MExpr
q -> MExpr
extE MExpr -> MExpr -> MExpr
`a` (MExpr
constE MExpr -> MExpr -> MExpr
`a` MExpr
q) MExpr -> MExpr -> MExpr
`a` MExpr
p),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f g :: MExpr
g -> MExpr
uncurryE MExpr -> MExpr -> MExpr
`a` ((MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
compE MExpr -> MExpr -> MExpr
`a` MExpr
g) MExpr -> MExpr -> MExpr
`c` MExpr
commaE MExpr -> MExpr -> MExpr
`c` MExpr
f))
(\f :: MExpr
f g :: MExpr
g -> MExpr
crossE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
g),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f -> MExpr
uncurryE MExpr -> MExpr -> MExpr
`a` (MExpr
commaE MExpr -> MExpr -> MExpr
`c` MExpr
f))
(\f :: MExpr
f -> MExpr
firstE MExpr -> MExpr -> MExpr
`a` MExpr
f),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\g :: MExpr
g -> MExpr
uncurryE MExpr -> MExpr -> MExpr
`a` ((MExpr
flipE MExpr -> MExpr -> MExpr
`a` MExpr
compE MExpr -> MExpr -> MExpr
`a` MExpr
g) MExpr -> MExpr -> MExpr
`c` MExpr
commaE))
(\g :: MExpr
g -> MExpr
secondE MExpr -> MExpr -> MExpr
`a` MExpr
g),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f -> MExpr
uncurryE MExpr -> MExpr -> MExpr
`a` (MExpr
constE MExpr -> MExpr -> MExpr
`a` MExpr
f))
(\f :: MExpr
f -> MExpr
f MExpr -> MExpr -> MExpr
`c` MExpr
sndE),
MExpr -> MExpr -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (MExpr
uncurryE MExpr -> MExpr -> MExpr
`a` MExpr
constE)
(MExpr
fstE),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f -> MExpr
uncurryE MExpr -> MExpr -> MExpr
`a` (MExpr
constE MExpr -> MExpr -> MExpr
`c` MExpr
f))
(\f :: MExpr
f -> MExpr
f MExpr -> MExpr -> MExpr
`c` MExpr
fstE),
RewriteRule -> RewriteRule
Hard (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\x :: MExpr
x -> MExpr
consE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
nilE)
(\x :: MExpr
x -> MExpr
returnE MExpr -> MExpr -> MExpr
`a` MExpr
x),
RewriteRule -> RewriteRule
Hard (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$
RewriteRule -> RewriteRule -> RewriteRule
If ([RewriteRule] -> RewriteRule
Or [MExpr -> MExpr -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr MExpr
consE MExpr
consE, MExpr -> MExpr -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr MExpr
nilE MExpr
nilE]) (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$ [RewriteRule] -> RewriteRule
Or [
RewriteRule -> RewriteRule
down (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$ [RewriteRule] -> RewriteRule
Or [
MExpr -> MExpr -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (MExpr
lengthE MExpr -> MExpr -> MExpr
`a` MExpr
nilE)
MExpr
zeroE,
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\x :: MExpr
x xs :: MExpr
xs -> MExpr
lengthE MExpr -> MExpr -> MExpr
`a` (MExpr
consE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
xs))
(\_ xs :: MExpr
xs -> MExpr
plusE MExpr -> MExpr -> MExpr
`a` MExpr
oneE MExpr -> MExpr -> MExpr
`a` (MExpr
lengthE MExpr -> MExpr -> MExpr
`a` MExpr
xs))
],
RewriteRule -> RewriteRule
down (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$ [RewriteRule] -> RewriteRule
Or [
(MExpr -> MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f x :: MExpr
x xs :: MExpr
xs -> MExpr
mapE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` (MExpr
consE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
xs))
(\f :: MExpr
f x :: MExpr
x xs :: MExpr
xs -> MExpr
consE MExpr -> MExpr -> MExpr
`a` (MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
x) MExpr -> MExpr -> MExpr
`a` (MExpr
mapE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
xs)),
(MExpr -> MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f x :: MExpr
x xs :: MExpr
xs -> MExpr
fmapE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` (MExpr
consE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
xs))
(\f :: MExpr
f x :: MExpr
x xs :: MExpr
xs -> MExpr
consE MExpr -> MExpr -> MExpr
`a` (MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
x) MExpr -> MExpr -> MExpr
`a` (MExpr
fmapE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
xs)),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f -> MExpr
mapE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
nilE)
(\_ -> MExpr
nilE),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f -> MExpr
fmapE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
nilE)
(\_ -> MExpr
nilE)
],
RewriteRule -> RewriteRule
down (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$ [RewriteRule] -> RewriteRule
Or [
(MExpr -> MExpr -> MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f x :: MExpr
x xs :: MExpr
xs z :: MExpr
z -> (MExpr
foldrE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
z) MExpr -> MExpr -> MExpr
`a` (MExpr
consE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
xs))
(\f :: MExpr
f x :: MExpr
x xs :: MExpr
xs z :: MExpr
z -> (MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
x) MExpr -> MExpr -> MExpr
`a` (MExpr
foldrE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
z MExpr -> MExpr -> MExpr
`a` MExpr
xs)),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f z :: MExpr
z -> MExpr
foldrE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
z MExpr -> MExpr -> MExpr
`a` MExpr
nilE)
(\_ z :: MExpr
z -> MExpr
z)
],
RewriteRule -> RewriteRule
down (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$ RewriteRule -> RewriteRule
Opt ((Expr -> Maybe Expr) -> RewriteRule
CRR ((Expr -> Maybe Expr) -> RewriteRule)
-> (Expr -> Maybe Expr) -> RewriteRule
forall a b. (a -> b) -> a -> b
$ [String] -> Expr -> Maybe Expr
assocL ["."]) RewriteRule -> RewriteRule -> RewriteRule
`Then` [RewriteRule] -> RewriteRule
Or [
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\xs :: MExpr
xs -> MExpr
sumE MExpr -> MExpr -> MExpr
`a` MExpr
xs)
(\xs :: MExpr
xs -> MExpr
foldlE MExpr -> MExpr -> MExpr
`a` MExpr
plusE MExpr -> MExpr -> MExpr
`a` MExpr
zeroE MExpr -> MExpr -> MExpr
`a` MExpr
xs),
(MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\xs :: MExpr
xs -> MExpr
productE MExpr -> MExpr -> MExpr
`a` MExpr
xs)
(\xs :: MExpr
xs -> MExpr
foldlE MExpr -> MExpr -> MExpr
`a` MExpr
multE MExpr -> MExpr -> MExpr
`a` MExpr
oneE MExpr -> MExpr -> MExpr
`a` MExpr
xs),
(MExpr -> MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f x :: MExpr
x xs :: MExpr
xs -> MExpr
foldl1E MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` (MExpr
consE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
xs))
(\f :: MExpr
f x :: MExpr
x xs :: MExpr
xs -> MExpr
foldlE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
xs),
(MExpr -> MExpr -> MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f z :: MExpr
z x :: MExpr
x xs :: MExpr
xs -> (MExpr
foldlE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
z) MExpr -> MExpr -> MExpr
`a` (MExpr
consE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
xs))
(\f :: MExpr
f z :: MExpr
z x :: MExpr
x xs :: MExpr
xs -> MExpr
foldlE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` (MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
z MExpr -> MExpr -> MExpr
`a` MExpr
x) MExpr -> MExpr -> MExpr
`a` MExpr
xs),
(MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f z :: MExpr
z -> MExpr
foldlE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
z MExpr -> MExpr -> MExpr
`a` MExpr
nilE)
(\_ z :: MExpr
z -> MExpr
z),
(MExpr -> MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f z :: MExpr
z x :: MExpr
x -> MExpr
foldlE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
z MExpr -> MExpr -> MExpr
`a` (MExpr
returnE MExpr -> MExpr -> MExpr
`a` MExpr
x))
(\f :: MExpr
f z :: MExpr
z x :: MExpr
x -> MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
z MExpr -> MExpr -> MExpr
`a` MExpr
x),
(MExpr -> MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr (\f :: MExpr
f z :: MExpr
z x :: MExpr
x -> MExpr
foldlE MExpr -> MExpr -> MExpr
`a` MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
z MExpr -> MExpr -> MExpr
`a` (MExpr
consE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
nilE))
(\f :: MExpr
f z :: MExpr
z x :: MExpr
x -> MExpr
f MExpr -> MExpr -> MExpr
`a` MExpr
z MExpr -> MExpr -> MExpr
`a` MExpr
x)
] RewriteRule -> RewriteRule -> RewriteRule
`OrElse` (
RewriteRule -> RewriteRule
Opt ((MExpr -> MExpr) -> (MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr0 (\x :: MExpr
x -> MExpr
consE MExpr -> MExpr -> MExpr
`a` MExpr
x)
(\x :: MExpr
x -> MExpr
appendE MExpr -> MExpr -> MExpr
`a` (MExpr
consE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
nilE))) RewriteRule -> RewriteRule -> RewriteRule
`Then`
RewriteRule -> RewriteRule
up ((MExpr -> MExpr -> MExpr)
-> (MExpr -> MExpr -> MExpr) -> RewriteRule
forall a. RewriteC a => a -> a -> RewriteRule
rr0 (\x :: MExpr
x ys :: MExpr
ys -> (MExpr
consE MExpr -> MExpr -> MExpr
`a` MExpr
x) MExpr -> MExpr -> MExpr
`c` (MExpr
appendE MExpr -> MExpr -> MExpr
`a` MExpr
ys))
(\x :: MExpr
x ys :: MExpr
ys -> MExpr
appendE MExpr -> MExpr -> MExpr
`a` (MExpr
consE MExpr -> MExpr -> MExpr
`a` MExpr
x MExpr -> MExpr -> MExpr
`a` MExpr
ys)))
)
],
(Expr -> Maybe Expr) -> RewriteRule
CRR (Expr -> Maybe Expr
collapseLists),
RewriteRule -> RewriteRule
up (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$ [RewriteRule] -> RewriteRule
Or [(Expr -> Maybe Expr) -> RewriteRule
CRR ([(String, Unary)] -> Expr -> Maybe Expr
evalUnary [(String, Unary)]
unaryBuiltins), (Expr -> Maybe Expr) -> RewriteRule
CRR ([(String, Binary)] -> Expr -> Maybe Expr
evalBinary [(String, Binary)]
binaryBuiltins)],
RewriteRule -> RewriteRule
up (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$ (Expr -> Maybe Expr) -> RewriteRule
CRR ([String] -> Expr -> Maybe Expr
assoc [String]
assocOps),
RewriteRule -> RewriteRule
up (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$ (Expr -> Maybe Expr) -> RewriteRule
CRR ([String] -> Expr -> Maybe Expr
assocL [String]
assocOps),
RewriteRule -> RewriteRule
up (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$ (Expr -> Maybe Expr) -> RewriteRule
CRR ([String] -> Expr -> Maybe Expr
assocR [String]
assocOps),
RewriteRule -> RewriteRule -> RewriteRule
Up ((Expr -> Maybe Expr) -> RewriteRule
CRR ([String] -> Expr -> Maybe Expr
commutative [String]
commutativeOps)) (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$ RewriteRule -> RewriteRule
down (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$ [RewriteRule] -> RewriteRule
Or [(Expr -> Maybe Expr) -> RewriteRule
CRR ((Expr -> Maybe Expr) -> RewriteRule)
-> (Expr -> Maybe Expr) -> RewriteRule
forall a b. (a -> b) -> a -> b
$ [String] -> Expr -> Maybe Expr
assocL [String]
assocLOps,
(Expr -> Maybe Expr) -> RewriteRule
CRR ((Expr -> Maybe Expr) -> RewriteRule)
-> (Expr -> Maybe Expr) -> RewriteRule
forall a b. (a -> b) -> a -> b
$ [String] -> Expr -> Maybe Expr
assocR [String]
assocROps],
RewriteRule -> RewriteRule
Hard (RewriteRule -> RewriteRule) -> RewriteRule -> RewriteRule
forall a b. (a -> b) -> a -> b
$ RewriteRule
simplifies
] RewriteRule -> RewriteRule -> RewriteRule
`Then` RewriteRule -> RewriteRule
Opt (RewriteRule -> RewriteRule
up RewriteRule
simplifies)
assocLOps, assocROps, assocOps :: [String]
assocLOps :: [String]
assocLOps = ["+", "*", "&&", "||", "max", "min"]
assocROps :: [String]
assocROps = [".", "++"]
assocOps :: [String]
assocOps = [String]
assocLOps [String] -> [String] -> [String]
forall a. [a] -> [a] -> [a]
++ [String]
assocROps
commutativeOps :: [String]
commutativeOps :: [String]
commutativeOps = ["*", "+", "==", "/=", "max", "min"]
unaryBuiltins :: [(String,Unary)]
unaryBuiltins :: [(String, Unary)]
unaryBuiltins = [
("not", (Bool -> Bool) -> Unary
forall a b. (Read a, Show a, Read b, Show b) => (a -> b) -> Unary
UA (Bool -> Bool
not :: Bool -> Bool)),
("negate", (Integer -> Integer) -> Unary
forall a b. (Read a, Show a, Read b, Show b) => (a -> b) -> Unary
UA (Integer -> Integer
forall a. Num a => a -> a
negate :: Integer -> Integer)),
("signum", (Integer -> Integer) -> Unary
forall a b. (Read a, Show a, Read b, Show b) => (a -> b) -> Unary
UA (Integer -> Integer
forall a. Num a => a -> a
signum :: Integer -> Integer)),
("abs", (Integer -> Integer) -> Unary
forall a b. (Read a, Show a, Read b, Show b) => (a -> b) -> Unary
UA (Integer -> Integer
forall a. Num a => a -> a
abs :: Integer -> Integer))
]
binaryBuiltins :: [(String,Binary)]
binaryBuiltins :: [(String, Binary)]
binaryBuiltins = [
("+", (Integer -> Integer -> Integer) -> Binary
forall a b c.
(Read a, Show a, Read b, Show b, Read c, Show c) =>
(a -> b -> c) -> Binary
BA (Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
(+) :: Integer -> Integer -> Integer)),
("-", (Integer -> Integer -> Integer) -> Binary
forall a b c.
(Read a, Show a, Read b, Show b, Read c, Show c) =>
(a -> b -> c) -> Binary
BA ((-) :: Integer -> Integer -> Integer)),
("*", (Integer -> Integer -> Integer) -> Binary
forall a b c.
(Read a, Show a, Read b, Show b, Read c, Show c) =>
(a -> b -> c) -> Binary
BA (Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
(*) :: Integer -> Integer -> Integer)),
("^", (Integer -> Integer -> Integer) -> Binary
forall a b c.
(Read a, Show a, Read b, Show b, Read c, Show c) =>
(a -> b -> c) -> Binary
BA (Integer -> Integer -> Integer
forall a b. (Num a, Integral b) => a -> b -> a
(^) :: Integer -> Integer -> Integer)),
("<", (Integer -> Integer -> Bool) -> Binary
forall a b c.
(Read a, Show a, Read b, Show b, Read c, Show c) =>
(a -> b -> c) -> Binary
BA (Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
(<) :: Integer -> Integer -> Bool)),
(">", (Integer -> Integer -> Bool) -> Binary
forall a b c.
(Read a, Show a, Read b, Show b, Read c, Show c) =>
(a -> b -> c) -> Binary
BA (Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
(>) :: Integer -> Integer -> Bool)),
("==", (Integer -> Integer -> Bool) -> Binary
forall a b c.
(Read a, Show a, Read b, Show b, Read c, Show c) =>
(a -> b -> c) -> Binary
BA (Integer -> Integer -> Bool
forall a. Eq a => a -> a -> Bool
(==) :: Integer -> Integer -> Bool)),
("/=", (Integer -> Integer -> Bool) -> Binary
forall a b c.
(Read a, Show a, Read b, Show b, Read c, Show c) =>
(a -> b -> c) -> Binary
BA (Integer -> Integer -> Bool
forall a. Eq a => a -> a -> Bool
(/=) :: Integer -> Integer -> Bool)),
("<=", (Integer -> Integer -> Bool) -> Binary
forall a b c.
(Read a, Show a, Read b, Show b, Read c, Show c) =>
(a -> b -> c) -> Binary
BA (Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
(<=) :: Integer -> Integer -> Bool)),
(">=", (Integer -> Integer -> Bool) -> Binary
forall a b c.
(Read a, Show a, Read b, Show b, Read c, Show c) =>
(a -> b -> c) -> Binary
BA (Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
(>=) :: Integer -> Integer -> Bool)),
("div", (Integer -> Integer -> Integer) -> Binary
forall a b c.
(Read a, Show a, Read b, Show b, Read c, Show c) =>
(a -> b -> c) -> Binary
BA (Integer -> Integer -> Integer
forall a. Integral a => a -> a -> a
div :: Integer -> Integer -> Integer)),
("mod", (Integer -> Integer -> Integer) -> Binary
forall a b c.
(Read a, Show a, Read b, Show b, Read c, Show c) =>
(a -> b -> c) -> Binary
BA (Integer -> Integer -> Integer
forall a. Integral a => a -> a -> a
mod :: Integer -> Integer -> Integer)),
("max", (Integer -> Integer -> Integer) -> Binary
forall a b c.
(Read a, Show a, Read b, Show b, Read c, Show c) =>
(a -> b -> c) -> Binary
BA (Integer -> Integer -> Integer
forall a. Ord a => a -> a -> a
max :: Integer -> Integer -> Integer)),
("min", (Integer -> Integer -> Integer) -> Binary
forall a b c.
(Read a, Show a, Read b, Show b, Read c, Show c) =>
(a -> b -> c) -> Binary
BA (Integer -> Integer -> Integer
forall a. Ord a => a -> a -> a
min :: Integer -> Integer -> Integer)),
("&&", (Bool -> Bool -> Bool) -> Binary
forall a b c.
(Read a, Show a, Read b, Show b, Read c, Show c) =>
(a -> b -> c) -> Binary
BA (Bool -> Bool -> Bool
(&&) :: Bool -> Bool -> Bool)),
("||", (Bool -> Bool -> Bool) -> Binary
forall a b c.
(Read a, Show a, Read b, Show b, Read c, Show c) =>
(a -> b -> c) -> Binary
BA (Bool -> Bool -> Bool
(||) :: Bool -> Bool -> Bool))
]