@@ -1,11 +1,88 @@
1Generating Data and Functions at Compile Time
1Generating Data and Functions at Compile Time
2=============================================
2=============================================
4−We can construct a data structure at compile-time in an Elab monad.
4+We can construct a datatype at compile-time in an Elab monad.
5This can allow proofs to be generated for user defined types or it could allow types to be automatically generated to support user defined types.
5This can allow proofs to be generated for user defined types or it could allow types to be automatically generated to support user defined types.
6An example is the code, from `Elaborator reflection: extending Idris in Idris`_, that automatically generates accessibility predicates using the Bove-Capretta method.
6An example is the code, from `Elaborator reflection: extending Idris in Idris`_, that automatically generates accessibility predicates using the Bove-Capretta method.
7−The following simple outline example is adapted from
7+
8−`<https://github.com/idris-lang/Idris-dev/blob/master/test/meta002/DataDef.idr>`_
8+Here is a simple example constucting a boolean type:
13+ %language ElabReflection
16+ addTwo = do let twoname : TTName = `{{TwoDef.Two}}
17+ declareDatatype $ Declare twoname [] `(Type)
18+ defineDatatype $ DefineDatatype twoname [
19+ Constructor `{{F}} [] (Var `{{TwoDef.Two}}),
20+ Constructor `{{T}} [] (Var `{{TwoDef.Two}})
27+ * - This type is now availible to us as if we had compiled it in the usual way:
28+ - .. code-block:: idris
31+ data Two : Type where
35+ * - The constructors are T and F:
36+ - .. code-block:: idris
43+We can now add some function definitions to the above code:
47+ let perm1 = `{{TwoDef.perm1}}
48+ let F2 = `{{TwoDef.F}}
49+ let T2 = `{{TwoDef.T}}
50+ declareType (Declare perm1 [MkFunArg `{{code}} (Var twoname) Explicit NotErased] (Var twoname))
51+ defineFunction $ DefineFun perm1 [
52+ MkFunClause (Var F2) (Var F2),
53+ MkFunClause (Var T2) (Var T2)
56+ let perm2 = `{{TwoDef.perm2}}
57+ declareType (Declare perm2 [MkFunArg `{{code}} (Var twoname) Explicit NotErased] (Var twoname))
58+ defineFunction $ DefineFun perm2 [
59+ MkFunClause (Var F2) (Var T2),
60+ MkFunClause (Var T2) (Var F2)
65+ * - Here are the functions:
66+ - .. code-block:: idris
77+ * - This is what happens when we call the functions:
78+ - .. code-block:: idris
85+Here is an example with parameters:
10.. code-block:: idris
87.. code-block:: idris
@@ -18,9 +95,9 @@ The following simple outline example is adapted from
18 declareDatatype $ Declare dataname [MkFunArg `{{n}} `(Nat) Explicit NotErased] `(Type)
95 declareDatatype $ Declare dataname [MkFunArg `{{n}} `(Nat) Explicit NotErased] `(Type)
19 defineDatatype $ DefineDatatype dataname [
96 defineDatatype $ DefineDatatype dataname [
20 Constructor `{{MkN}} [MkFunArg `{{x}} `(Nat) Implicit NotErased]
97 Constructor `{{MkN}} [MkFunArg `{{x}} `(Nat) Implicit NotErased]
21− (RApp (Var `{{DataDef.N}}) (Var `{{x}})),
98+ (RApp (Var dataname) (Var `{{x}})),
22 Constructor `{{MkN'}} [MkFunArg `{{x}} `(Nat) Explicit NotErased]
99 Constructor `{{MkN'}} [MkFunArg `{{x}} `(Nat) Explicit NotErased]
23− (RApp (Var `{{DataDef.N}}) (RApp (Var `{S}) (Var `{{x}})))
100+ (RApp (Var dataname) (RApp (Var `{S}) (Var `{{x}})))
26 %runElab addData
103 %runElab addData
@@ -46,80 +123,8 @@ Which can be used like this:
46 λΠ> :t MkN
123 λΠ> :t MkN
47 MkN : N x
124 MkN : N x
49−Here is another, more complicated, example from the same test file. This also creates a function.
54− %language ElabReflection
58− let U = `{{DataDef.U}}
59− let el = `{{DataDef.el}}
60− declareDatatype $ Declare U [] `(Type)
61− declareType $ Declare el [MkFunArg `{{code}} (Var U) Explicit NotErased] `(Type)
62− defineDatatype $ DefineDatatype U [
63− Constructor `{{Base}} [] (Var U),
65− [MkFunArg `{{code}} (Var U) Explicit NotErased,
66− MkFunArg `{{body}} `(~(RApp (Var el) (Var `{{code}})) -> ~(Var U)) Explicit NotErased]
69− defineFunction $ DefineFun el [
70− MkFunClause (RBind `{{code}} (PVar (Var U))
71− (RBind `{{body}} (PVar `(~(RApp (Var el) (Var `{{code}})) -> ~(Var U)))
73− (RApp (RApp (Var `{{DataDef.Pi}})
76− (RBind `{{code}} (PVar (Var U))
77− (RBind `{{body}} (PVar `(~(RApp (Var el) (Var `{{code}})) -> ~(Var U)))
78− (RBind `{{x}} (Pi (RApp (Var el) (Var `{{code}})) `(Type))
79− (RApp (Var el) (RApp (Var `{{body}}) (Var `{{x}})))))),
80− MkFunClause (RApp (Var el) (Var `{{DataDef.Base}})) `(Bool)
85−This code generates the following data and function:
91− Pi : (code : U) -> (el code -> U) -> U
93− el (Pi code body) = (x : el code) -> el (body x)
98− * - We can then use U the data structure, like this:
101− .. code-block:: idris
106− No documentation for U
110− Pi : (code : U) -> (el code -> U) -> U
112− * - el is the function that has been defined:
115− .. code-block:: idris
122−So these are the functions that we can use to create data and functions in the Elab monad:
127+These are the functions that we can use to create data and functions in the Elab monad:
124.. list-table:: Generating Data and Functions
129.. list-table:: Generating Data and Functions
125 :widths: 10 30
130 :widths: 10 30
@@ -153,8 +158,10 @@ So these are the functions that we can use to create data and functions in the E
153 * - addImplementation
158 * - addImplementation
154 - Register a new implementation for interface resolution.
159 - Register a new implementation for interface resolution.
156− - @ ifaceName the name of the interface for which an implementation is being registered
163+ - ifaceName the name of the interface for which an implementation is being registered
157− - @ implName the name of the definition to use in implementation search
164+ - implName the name of the definition to use in implementation search
159 Signature:
166 Signature:
@@ -163,7 +170,9 @@ So these are the functions that we can use to create data and functions in the E
163 * - isTCName
170 * - isTCName
164 - Determine whether a name denotes an interface.
171 - Determine whether a name denotes an interface.
166− @ name a name that might denote an interface.
175+ - name - a name that might denote an interface.
168 Signature:
177 Signature: