-
Notifications
You must be signed in to change notification settings - Fork 0
/
SchemaInstance.cs
executable file
·143 lines (126 loc) · 2.85 KB
/
SchemaInstance.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
using System;
using System.Text;
using System.Text.RegularExpressions;
using System.Diagnostics;
using System.Collections;
namespace FileWalk.Schema
{
/// <summary>
/// Define common members and methods of StructInstance and ArrayInstance.
/// </summary>
public abstract class ElementInstance
{
/// <summary>
/// The parent of this instance in structure hierarchy.
/// </summary>
protected ElementInstance _parent;
public ElementInstance(ElementInstance parent)
{
_parent = parent;
}
/// <summary>
/// Evaluate specified expression.
/// </summary>
public abstract object Eval(string expr);
}
/// <summary>
/// The instance of an struct element.
/// </summary>
public class StructInstance : ElementInstance
{
private Hashtable _memberOfName = new Hashtable();
private Element[] _elements;
public StructInstance(ElementInstance parent, Element[] elements) : base(parent)
{
_elements = elements;
}
public object this[string name]
{
get
{
return _memberOfName[name];
}
set
{
_memberOfName[name] = value;
}
}
public IEnumerable Elements
{
get
{
if (_elements == null)
{
_elements = new Element[0];
}
return _elements;
}
}
public Hashtable Members
{
get
{
if (_memberOfName == null)
{
_memberOfName = new Hashtable();
}
return _memberOfName;
}
}
/// <summary>
/// Evaluate given expression to value.
/// </summary>
/// <param name="expr">format: a.b.c.d</param>
public override object Eval(string expr)
{
string[] names = expr.Split(new char[] {'.'});
object val = (names[0] == "parent") ?
_parent : // parent object
this[names[0]]; // lookup by name
if (val is StructInstance)
{
// rebuild the rest of names.
StringBuilder sb = new StringBuilder();
for (int i = 1; i < names.Length; i++)
{
if (sb.Length > 0)
{
sb.Append('.');
}
sb.Append(names[i]);
}
return (val as StructInstance).Eval(sb.ToString());
}
else
{
return val;
}
}
}
public class ArrayInstance : ElementInstance
{
public Element Type;
public Object[] Elements;
public ArrayInstance(ElementInstance parent, Element type, Object[] elements) : base(parent)
{
this.Type = type;
this.Elements = elements;
}
/// <summary>
/// To evaluate "[index]" to access array element.
/// </summary>
/// <param name="expr"></param>
/// <returns></returns>
public override object Eval(string expr)
{
Regex regexIndexer = new Regex(@"\[(.*)\]");
Match match = regexIndexer.Match(expr);
if (match.Success)
{
int index = Int32.Parse(match.Groups[1].Value);
return Elements[index];
}
return null;
}
}
}