1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22 package jTrolog.engine;
23
24 import jTrolog.errors.PrologException;
25 import jTrolog.parser.Parser;
26 import jTrolog.lib.Library;
27 import jTrolog.lib.BuiltIn;
28 import jTrolog.terms.Struct;
29 import jTrolog.terms.Term;
30 import jTrolog.terms.Clause;
31
32 import java.io.Serializable;
33 import java.util.*;
34 import java.lang.reflect.InvocationTargetException;
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57 @SuppressWarnings({ "rawtypes", "unchecked","serial" })
58 class LibraryAndTheoryManager implements Serializable {
59
60 private ClauseDatabase dynamicDBase;
61 private ClauseDatabase allLibraryRules;
62
63 private LinkedHashMap librariesToRules;
64
65 private Prolog engine;
66 String lastConsultedTheory;
67
68 LibraryAndTheoryManager(Prolog vm) {
69 dynamicDBase = new ClauseDatabase();
70 librariesToRules = new LinkedHashMap();
71 allLibraryRules = new ClauseDatabase();
72 lastConsultedTheory = "";
73 engine = vm;
74 }
75
76
77
78
79 void assertA(Clause clause, String index) throws PrologException {
80 dynamicDBase.addFirst(index, clause);
81 }
82
83
84
85
86 void assertZ(Clause clause, String index) throws PrologException {
87 dynamicDBase.addLast(index, clause);
88 }
89
90
91
92
93
94 Struct retract(Struct clause, String index) throws PrologException {
95 LinkedList family = (LinkedList) dynamicDBase.get(index);
96 if (family == null)
97 return null;
98 for (Iterator it = family.iterator(); it.hasNext();) {
99 Clause d = (Clause) it.next();
100 if (Prolog.match(clause, d.original)) {
101 it.remove();
102 return d.original;
103 }
104 }
105 return null;
106 }
107
108
109
110
111 List abolish(String index) throws PrologException {
112 return dynamicDBase.abolish(index);
113 }
114
115
116
117
118 public void setDynamic(String index) {
119 LinkedList family = (LinkedList) dynamicDBase.get(index);
120 if (family != null)
121 return;
122 dynamicDBase.addFirst(index, Term.emptyList);
123 family = (LinkedList) dynamicDBase.get(index);
124 for (Iterator it = family.iterator(); it.hasNext();) {
125 it.next();
126 it.remove();
127 }
128 }
129
130
131
132
133
134 List find(String predIndicator) throws PrologException {
135 List dynamics = dynamicDBase.getPredicatesIterator(predIndicator);
136 return dynamics != null ? dynamics : allLibraryRules.getPredicatesIterator(predIndicator);
137 }
138
139
140
141
142
143
144
145
146 void consult(String theory) throws PrologException {
147 lastConsultedTheory = theory;
148
149 for (Iterator it = new Parser(theory, engine).iterator(); it.hasNext();) {
150 Struct d = (Struct) it.next();
151 if (runDirective(d))
152 continue;
153
154 Clause cl = BuiltIn.convertTermToClause(d);
155 assertZ(cl, cl.head.predicateIndicator);
156 }
157 }
158
159
160
161
162 void clear() {
163 dynamicDBase.clear();
164 }
165
166 private boolean runDirective(Struct c) {
167 if (c.predicateIndicator != Parser.singleClauseSignature)
168 return false;
169 Term dir = c.getArg(0);
170 if (!(dir instanceof Struct))
171 return false;
172 try {
173 try {
174 PrimitiveInfo directive = engine.getPrimitive((Struct) dir);
175 if (directive == null)
176 engine.warn("The directive " + ((Struct) dir).predicateIndicator + " is unknown.");
177 else {
178 Object[] args = new Object[((Struct) dir).arity + 1];
179 args[0] = new BindingsTable();
180 for (int i = 0; i < ((Struct) dir).arity; i++)
181 args[i + 1] = ((Struct) dir).getArg(i);
182 Prolog.evalPrimitive(directive, args);
183 }
184 } catch (InvocationTargetException e) {
185 Throwable cause = e;
186 while (cause instanceof InvocationTargetException)
187 cause = cause.getCause();
188 throw cause;
189 }
190 } catch (Throwable cause) {
191 engine.warn("An exception has been thrown during the execution of the " + ((Struct) dir).predicateIndicator + " directive.\n" + cause.getMessage());
192 }
193 return true;
194 }
195
196
197
198
199
200
201
202 public String getTheory(boolean onlyDynamic) {
203 if (onlyDynamic)
204 return dynamicDBase.toString();
205 return dynamicDBase.toString() + "\n\n" + allLibraryRules.toString();
206 }
207
208
209
210
211
212
213 String getLastConsultedTheory() {
214 return lastConsultedTheory;
215 }
216
217 boolean isLibraryRule(String key) {
218 return allLibraryRules.containsKey(key);
219 }
220
221
222
223
224
225
226
227 Iterator dynamicPredicateIndicators() {
228 return dynamicDBase.keySet().iterator();
229 }
230
231 Library consultLib(Library lib) throws PrologException {
232
233 ClauseDatabase theoryAssociated = new ClauseDatabase();
234 for (Iterator it = new Parser(lib.getTheory(), engine).iterator(); it.hasNext();) {
235 Struct d = (Struct) it.next();
236 if (runDirective(d))
237 continue;
238 Clause cl = BuiltIn.convertTermToClause(d);
239 theoryAssociated.addLast(cl.head.predicateIndicator, cl);
240 allLibraryRules.addLast(cl.head.predicateIndicator, cl);
241 }
242 librariesToRules.put(lib, theoryAssociated);
243 return lib;
244 }
245
246 Library unconsultLib(Library lib) {
247 lib.dismiss();
248 ClauseDatabase removed = (ClauseDatabase) librariesToRules.remove(lib);
249 for (Iterator it = removed.keySet().iterator(); it.hasNext();) {
250 String predInfo = (String) it.next();
251 List toBeRemoved = (List) removed.get(predInfo);
252 List parentList = allLibraryRules.getPredicates(predInfo);
253 for (int i = 0; i < toBeRemoved.size(); i++)
254 parentList.remove(toBeRemoved.get(i));
255 }
256 return lib;
257 }
258
259 Library getLibrary(String name) {
260 for (Iterator it = getCurrentLibraries(); it.hasNext();) {
261 Library lib = (Library) it.next();
262 if (name.equals(lib.getName()))
263 return lib;
264 }
265 return null;
266 }
267
268
269
270
271 Iterator getCurrentLibraries() {
272 return librariesToRules.keySet().iterator();
273 }
274 }