1 module orelang.expression.Macro;
2 import orelang.expression.IExpression,
3        orelang.Engine,
4        orelang.Value;
5 import std..string,
6        std.conv;
7 
8 class Macro {
9   string   macro_name;
10   string[] macro_args;
11   Value    macro_body;
12 
13   this(string name, string[] args, Value _body) {
14     this.macro_name = name;
15     this.macro_args = args;
16     this.macro_body = _body;
17   }
18 
19   public Value call(Engine engine, Value[] args) {
20     import std.stdio;
21 
22     Value[string] convList;
23 
24     foreach (idx, arg; macro_args) {
25       convList[arg] = args[idx];
26     }
27 
28     Value[] analysis(Value source) {
29       Value[] dist;
30 
31       if (source.type == ValueType.Array) {
32         foreach (elem; source.getArray) {
33           if (elem.type == ValueType.Array) {
34             dist ~= new Value(analysis(elem));
35           } else {
36             if (elem.type == ValueType.SymbolValue) {
37               if (elem.getString in convList) {
38                 elem = convList[elem.getString];
39               }
40             }
41 
42             dist ~= elem;
43           }
44         }
45       } else {
46         dist ~= source;
47       }
48 
49       return dist;
50     }
51 
52     return engine.eval(new Value(analysis(this.macro_body)));
53   }
54 
55   override string toString() {
56     return "Macro";
57   }
58 }