Safe Haskell | None |
---|---|
Language | Haskell2010 |
Generic representation of typed syntax trees
For details, see: A Generic Abstract Syntax Model for Embedded Languages (ICFP 2012, https://emilaxelsson.github.io/documents/axelsson2012generic.pdf).
Synopsis
- data AST sym sig where
- type ASTF sym a = AST sym (Full a)
- newtype ASTFull sym a = ASTFull {}
- newtype Full a = Full {
- result :: a
- newtype a :-> sig = Partial (a -> sig)
- data SigRep sig where
- class Signature sig where
- type family DenResult sig
- class Symbol sym where
- size :: AST sym sig -> Int
- type family SmartFun (sym :: * -> *) sig
- type family SmartSig f
- type family SmartSym f :: * -> *
- smartSym' :: forall sig f sym. (Signature sig, f ~ SmartFun sym sig, sig ~ SmartSig f, sym ~ SmartSym f) => sym sig -> f
- data (sym1 :+: sym2) sig where
- class Project sub sup where
- class Project sub sup => sub :<: sup where
- inj :: sub a -> sup a
- smartSym :: (Signature sig, f ~ SmartFun sup sig, sig ~ SmartSig f, sup ~ SmartSym f, sub :<: sup) => sub sig -> f
- smartSymTyped :: (Signature sig, f ~ SmartFun (Typed sup) sig, sig ~ SmartSig f, Typed sup ~ SmartSym f, sub :<: sup, Typeable (DenResult sig)) => sub sig -> f
- data Empty :: * -> *
- data E e where
- liftE :: (forall a. e a -> b) -> E e -> b
- liftE2 :: (forall a b. e a -> e b -> c) -> E e -> E e -> c
- data EF e where
- liftEF :: (forall a. e (Full a) -> b) -> EF e -> b
- liftEF2 :: (forall a b. e (Full a) -> e (Full b) -> c) -> EF e -> EF e -> c
- data Typed sym sig where
- injT :: (sub :<: sup, Typeable (DenResult sig)) => sub sig -> AST (Typed sup) sig
- castExpr :: forall sym a b. ASTF (Typed sym) a -> ASTF (Typed sym) b -> Maybe (ASTF (Typed sym) b)
- class NFData1 c where
- rnf1 :: c a -> ()
- symType :: Proxy sym -> sym sig -> sym sig
- prjP :: Project sub sup => Proxy sub -> sup sig -> Maybe (sub sig)
Syntax trees
data AST sym sig where Source #
Generic abstract syntax tree, parameterized by a symbol domain
(
represents a partially applied (or unapplied)
symbol, missing at least one argument, while AST
sym (a :->
b))(
represents a fully applied symbol, i.e. a complete syntax tree.AST
sym (Full
a))
Sym :: sym sig -> AST sym sig | |
(:$) :: AST sym (a :-> sig) -> AST sym (Full a) -> AST sym sig infixl 1 |
Instances
sub :<: sup => sub :<: (AST sup) Source # | |
Defined in Language.Syntactic.Syntax | |
Project sub sup => Project sub (AST sup) Source # | |
Functor sym => Functor (AST sym) Source # | |
Equality sym => Equality (AST sym) Source # | |
BindingDomain sym => BindingDomain (AST sym) Source # | |
Equality sym => Eq (AST sym a) Source # | |
Render sym => Show (ASTF sym a) Source # | |
NFData1 sym => NFData (AST sym sig) Source # | |
Defined in Language.Syntactic.Syntax | |
Syntactic (ASTF sym a) Source # | |
(Syntactic a, Domain a ~ sym, ia ~ Internal a, SyntacticN f fi) => SyntacticN (a -> f) (AST sym (Full ia) -> fi) Source # | |
type SmartSym (AST sym sig) Source # | |
Defined in Language.Syntactic.Syntax | |
type SmartSig (ASTF sym a -> f) Source # | |
Defined in Language.Syntactic.Syntax | |
type SmartSig (AST sym sig) Source # | |
Defined in Language.Syntactic.Syntax | |
type Domain (ASTF sym a) Source # | |
Defined in Language.Syntactic.Sugar | |
type Internal (ASTF sym a) Source # | |
Defined in Language.Syntactic.Sugar |
newtype ASTFull sym a Source #
Fully applied abstract syntax tree
This type is like AST
, but being a newtype, it is a proper type constructor
that can be partially applied.
Instances
Syntactic (ASTFull sym a) Source # | |
Defined in Language.Syntactic.Sugar | |
type Domain (ASTFull sym a) Source # | |
Defined in Language.Syntactic.Sugar | |
type Internal (ASTFull sym a) Source # | |
Defined in Language.Syntactic.Sugar |
Signature of a fully applied symbol
Instances
Functor Full Source # | |
Eq a => Eq (Full a) Source # | |
Show a => Show (Full a) Source # | |
Signature (Full a) Source # | |
Render sym => Show (ASTF sym a) Source # | |
Syntactic (ASTF sym a) Source # | |
(Syntactic a, Domain a ~ sym, ia ~ Internal a, SyntacticN f fi) => SyntacticN (a -> f) (AST sym (Full ia) -> fi) Source # | |
type SmartFun sym (Full a) Source # | |
Defined in Language.Syntactic.Syntax | |
type DenotationM m (Full a) Source # | |
Defined in Language.Syntactic.Functional | |
type LiftReader env (Full a) Source # | |
Defined in Language.Syntactic.Functional.WellScoped | |
type DenResult (Full a) Source # | |
Defined in Language.Syntactic.Syntax | |
type Denotation (Full a) Source # | |
Defined in Language.Syntactic.Functional | |
type LowerReader (Full a) Source # | |
Defined in Language.Syntactic.Functional.WellScoped | |
type SmartSig (ASTF sym a -> f) Source # | |
Defined in Language.Syntactic.Syntax | |
type Domain (ASTF sym a) Source # | |
Defined in Language.Syntactic.Sugar | |
type Internal (ASTF sym a) Source # | |
Defined in Language.Syntactic.Sugar |
newtype a :-> sig infixr 9 Source #
Signature of a partially applied (or unapplied) symbol
Partial (a -> sig) |
Instances
Functor ((:->) a) Source # | |
Signature sig => Signature (a :-> sig) Source # | |
type SmartFun sym (a :-> sig) Source # | |
Defined in Language.Syntactic.Syntax | |
type DenotationM m (a :-> sig) Source # | |
Defined in Language.Syntactic.Functional | |
type LiftReader env (a :-> sig) Source # | |
Defined in Language.Syntactic.Functional.WellScoped | |
type DenResult (a :-> sig) Source # | |
Defined in Language.Syntactic.Syntax | |
type Denotation (a :-> sig) Source # | |
Defined in Language.Syntactic.Functional | |
type LowerReader (a :-> sig) Source # | |
Defined in Language.Syntactic.Functional.WellScoped |
class Symbol sym where Source #
Valid symbols to use in an AST
Instances
Smart constructors
type family SmartFun (sym :: * -> *) sig Source #
Maps a symbol signature to the type of the corresponding smart constructor:
SmartFun sym (a :-> b :-> ... :-> Full x) = ASTF sym a -> ASTF sym b -> ... -> ASTF sym x
type family SmartSig f Source #
Maps a smart constructor type to the corresponding symbol signature:
SmartSig (ASTF sym a -> ASTF sym b -> ... -> ASTF sym x) = a :-> b :-> ... :-> Full x
smartSym' :: forall sig f sym. (Signature sig, f ~ SmartFun sym sig, sig ~ SmartSig f, sym ~ SmartSym f) => sym sig -> f Source #
Make a smart constructor of a symbol. smartSym'
has any type of the form:
smartSym' :: sym (a :-> b :-> ... :-> Full x) -> (ASTF sym a -> ASTF sym b -> ... -> ASTF sym x)
Open symbol domains
data (sym1 :+: sym2) sig where infixr 9 Source #
Direct sum of two symbol domains
Instances
sym1 :<: sym3 => sym1 :<: (sym2 :+: sym3) Source # | |
Defined in Language.Syntactic.Syntax | |
sym1 :<: (sym1 :+: sym2) Source # | |
Defined in Language.Syntactic.Syntax | |
Project sym1 sym3 => Project sym1 (sym2 :+: sym3) Source # | |
Project sym1 (sym1 :+: sym2) Source # | |
(Functor sym1, Functor sym2) => Functor (sym1 :+: sym2) Source # | |
(Foldable sym1, Foldable sym2) => Foldable (sym1 :+: sym2) Source # | |
Defined in Language.Syntactic.Syntax fold :: Monoid m => (sym1 :+: sym2) m -> m # foldMap :: Monoid m => (a -> m) -> (sym1 :+: sym2) a -> m # foldMap' :: Monoid m => (a -> m) -> (sym1 :+: sym2) a -> m # foldr :: (a -> b -> b) -> b -> (sym1 :+: sym2) a -> b # foldr' :: (a -> b -> b) -> b -> (sym1 :+: sym2) a -> b # foldl :: (b -> a -> b) -> b -> (sym1 :+: sym2) a -> b # foldl' :: (b -> a -> b) -> b -> (sym1 :+: sym2) a -> b # foldr1 :: (a -> a -> a) -> (sym1 :+: sym2) a -> a # foldl1 :: (a -> a -> a) -> (sym1 :+: sym2) a -> a # toList :: (sym1 :+: sym2) a -> [a] # null :: (sym1 :+: sym2) a -> Bool # length :: (sym1 :+: sym2) a -> Int # elem :: Eq a => a -> (sym1 :+: sym2) a -> Bool # maximum :: Ord a => (sym1 :+: sym2) a -> a # minimum :: Ord a => (sym1 :+: sym2) a -> a # | |
(Traversable sym1, Traversable sym2) => Traversable (sym1 :+: sym2) Source # | |
Defined in Language.Syntactic.Syntax traverse :: Applicative f => (a -> f b) -> (sym1 :+: sym2) a -> f ((sym1 :+: sym2) b) # sequenceA :: Applicative f => (sym1 :+: sym2) (f a) -> f ((sym1 :+: sym2) a) # mapM :: Monad m => (a -> m b) -> (sym1 :+: sym2) a -> m ((sym1 :+: sym2) b) # sequence :: Monad m => (sym1 :+: sym2) (m a) -> m ((sym1 :+: sym2) a) # | |
(NFData1 sym1, NFData1 sym2) => NFData1 (sym1 :+: sym2) Source # | |
Defined in Language.Syntactic.Syntax | |
(Symbol sym1, Symbol sym2) => Symbol (sym1 :+: sym2) Source # | |
(StringTree sym1, StringTree sym2) => StringTree (sym1 :+: sym2) Source # | |
Defined in Language.Syntactic.Interpretation | |
(Render sym1, Render sym2) => Render (sym1 :+: sym2) Source # | |
(Equality sym1, Equality sym2) => Equality (sym1 :+: sym2) Source # | |
(Eval s, Eval t) => Eval (s :+: t) Source # | |
Defined in Language.Syntactic.Functional evalSym :: (s :+: t) sig -> Denotation sig Source # | |
(BindingDomain sym1, BindingDomain sym2) => BindingDomain (sym1 :+: sym2) Source # | |
(EvalEnv sym1 env, EvalEnv sym2 env) => EvalEnv (sym1 :+: sym2) env Source # | |
Defined in Language.Syntactic.Functional compileSym :: proxy env -> (sym1 :+: sym2) sig -> DenotationM (Reader env) sig Source # | |
(Equality sym1, Equality sym2) => Eq ((sym1 :+: sym2) a) Source # | |
class Project sub sup where Source #
Symbol projection
The class is defined for all pairs of types, but prj
can only succeed if sup
is of the form
(...
.:+:
sub :+:
...)
Instances
Project sym sym Source # | |
Defined in Language.Syntactic.Syntax | |
Project sub sup => Project sub (Typed sup) Source # | |
Project sub sup => Project sub (AST sup) Source # | |
Project sym1 sym3 => Project sym1 (sym2 :+: sym3) Source # | |
Project sym1 (sym1 :+: sym2) Source # | |
Project sub sup => Project sub (sup :&: info) Source # | |
class Project sub sup => sub :<: sup where Source #
Symbol injection
The class includes types sub
and sup
where sup
is of the form (...
.:+:
sub :+:
...)
Instances
smartSym :: (Signature sig, f ~ SmartFun sup sig, sig ~ SmartSig f, sup ~ SmartSym f, sub :<: sup) => sub sig -> f Source #
Make a smart constructor of a symbol. smartSym
has any type of the form:
smartSym :: (sub :<: AST sup) => sub (a :-> b :-> ... :-> Full x) -> (ASTF sup a -> ASTF sup b -> ... -> ASTF sup x)
smartSymTyped :: (Signature sig, f ~ SmartFun (Typed sup) sig, sig ~ SmartSig f, Typed sup ~ SmartSym f, sub :<: sup, Typeable (DenResult sig)) => sub sig -> f Source #
Make a smart constructor of a symbol. smartSymTyped
has any type of the
form:
smartSymTyped :: (sub :<: AST (Typed sup), Typeable x) => sub (a :-> b :-> ... :-> Full x) -> (ASTF sup a -> ASTF sup b -> ... -> ASTF sup x)
Empty symbol type
Can be used to make uninhabited AST
types. It can also be used as a terminator in co-product
lists (e.g. to avoid overlapping instances):
(A :+: B :+: Empty)
Instances
StringTree Empty Source # | |
Defined in Language.Syntactic.Interpretation | |
Render Empty Source # | |
Equality Empty Source # | |
Eval Empty Source # | |
Defined in Language.Syntactic.Functional evalSym :: Empty sig -> Denotation sig Source # | |
EvalEnv Empty env Source # | |
Defined in Language.Syntactic.Functional compileSym :: proxy env -> Empty sig -> DenotationM (Reader env) sig Source # |
Existential quantification
Type casting expressions
data Typed sym sig where Source #
"Typed" symbol. Using
instead of Typed
symsym
gives access to the
function castExpr
for casting expressions.
Instances
Project sub sup => Project sub (Typed sup) Source # | |
StringTree sym => StringTree (Typed sym) Source # | |
Defined in Language.Syntactic.Interpretation | |
Render sym => Render (Typed sym) Source # | |
Equality sym => Equality (Typed sym) Source # | |
BindingDomain sym => BindingDomain (Typed sym) Source # | |
EvalEnv sym env => EvalEnv (Typed sym) env Source # | |
Defined in Language.Syntactic.Functional compileSym :: proxy env -> Typed sym sig -> DenotationM (Reader env) sig Source # |
:: forall sym a b. ASTF (Typed sym) a | Expression to cast |
-> ASTF (Typed sym) b | Witness for typeability of result |
-> Maybe (ASTF (Typed sym) b) |
Type cast an expression
Misc.
class NFData1 c where Source #
Higher-kinded version of NFData
Nothing
Instances
NFData1 BindingT Source # | |
Defined in Language.Syntactic.Functional | |
NFData1 Binding Source # | |
Defined in Language.Syntactic.Functional | |
NFData1 BindingWS Source # | |
Defined in Language.Syntactic.Functional.WellScoped | |
(NFData1 sym1, NFData1 sym2) => NFData1 (sym1 :+: sym2) Source # | |
Defined in Language.Syntactic.Syntax | |
(NFData1 sym, NFData1 info) => NFData1 (sym :&: info) Source # | |
Defined in Language.Syntactic.Decoration |