KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > com > genimen > djeneric > repository > oql > core > util > TreeNormalizer


1 package com.genimen.djeneric.repository.oql.core.util;
2
3 import com.genimen.djeneric.repository.oql.core.ParseException;
4 import com.genimen.djeneric.repository.oql.core.SimpleNode;
5 import com.genimen.djeneric.repository.oql.core.nodes.AndOrNode;
6 import com.genimen.djeneric.repository.oql.core.nodes.BracketNode;
7 import com.genimen.djeneric.repository.oql.core.nodes.CalculatedExpressionNode;
8 import com.genimen.djeneric.repository.oql.core.nodes.ExpressionNode;
9 import com.genimen.djeneric.repository.oql.core.nodes.OperatorNode;
10 import com.genimen.djeneric.repository.oql.core.nodes.SubExpressionNode;
11
12 public class TreeNormalizer
13 {
14
15   public TreeNormalizer()
16   {
17   }
18
19   public void normalize(SimpleNode root) throws ParseException
20   {
21     // The order of the following methods is NOT trivial
22
pruneBrackets(root);
23     normalizeOperands(root);
24     pruneCalculatedExpressions(root);
25     normalizeAndOr(root);
26     pruneUnary(root);
27
28     minimizeBrackets(root);
29   }
30
31   private void minimizeBrackets(SimpleNode root) throws ParseException
32   {
33     int open = root.getBracketOpenCount();
34     int close = root.getBracketCloseCount();
35
36     if (open > 1 && close > 1)
37     {
38       root.setBracketOpenCount((open - Math.min(open, close)) + 1);
39       root.setBracketCloseCount((close - Math.min(open, close)) + 1);
40     }
41     if (root.getChildCount() == 0)
42     {
43       root.setBracketOpenCount(0);
44       root.setBracketCloseCount(0);
45     }
46
47     for (int i = 0; i < root.getChildCount(); i++)
48     {
49       minimizeBrackets(root.getChild(i));
50     }
51   }
52
53   private void pruneBrackets(SimpleNode root) throws ParseException
54   {
55     int i = 0;
56     while (i < root.getChildCount())
57     {
58       if (root.getChild(i) instanceof BracketNode)
59       {
60         String JavaDoc br = ((BracketNode) root.getChild(i)).getBracket();
61         int countOpen = root.getChild(i).getBracketOpenCount();
62         int countClose = root.getChild(i).getBracketOpenCount();
63         root.removeChild(i);
64         int idx = i;
65
66         if (br.equals(")")) idx--;
67
68         root.getChild(idx).increaseCloseBracket(countClose);
69         root.getChild(idx).increaseOpenBracket(countOpen);
70
71         if (br.equals("(")) root.getChild(idx).increaseOpenBracket(1);
72         else if (br.equals(")")) root.getChild(idx).increaseCloseBracket(1);
73       }
74       else i++;
75     }
76
77     for (i = 0; i < root.getChildCount(); i++)
78     {
79       pruneBrackets(root.getChild(i));
80     }
81   }
82
83   private void pushDown(CalculatedExpressionNode expr, String JavaDoc operator)
84   {
85     int i = 1;
86
87     while (i < expr.getChildCount() - 1)
88     {
89       int increment = 1;
90       SimpleNode child = expr.getChild(i);
91       if (child instanceof OperatorNode)
92       {
93         OperatorNode opNode = (OperatorNode) child;
94         if ((operator.equals("+-") && (opNode.getOperator().equals("+") || opNode.getOperator().equals("-")))
95             || (opNode.getOperator().equals(operator)))
96         {
97           moveLeftRightDown(expr, i, opNode);
98           // We shuffled the children; the 'next' is now the current because
99
// the left node is removed from the children list.
100
increment = 0;
101         }
102       }
103       i += increment;
104       // proceed with next node
105
}
106   }
107
108   private void pushDown(ExpressionNode expr, String JavaDoc andor)
109   {
110     int i = 1;
111
112     while (i < expr.getChildCount() - 1)
113     {
114       int increment = 1;
115       SimpleNode child = expr.getChild(i);
116       if (child instanceof AndOrNode)
117       {
118         AndOrNode aoNode = (AndOrNode) child;
119         if (aoNode.getOperator().equals(andor))
120         {
121           moveLeftRightDown(expr, i, aoNode);
122           // We shuffled the children; the 'next' is now the current because
123
// the left node is removed from the children list.
124
increment = 0;
125         }
126       }
127       i += increment;
128       // proceed with next node
129
}
130   }
131
132   private void moveLeftRightDown(SimpleNode expr, int i, SimpleNode opNode)
133   {
134     SimpleNode left = expr.getChild(i - 1);
135     SimpleNode right = expr.getChild(i + 1);
136
137     expr.removeChild(left);
138     expr.removeChild(right);
139
140     left.setParent(opNode);
141     right.setParent(opNode);
142
143     opNode.addChild(left);
144     opNode.addChild(right);
145   }
146
147   private void normalizeOperands(SimpleNode root)
148   {
149     for (int i = 0; i < root.getChildCount(); i++)
150     {
151       normalizeOperands(root.getChild(i));
152     }
153
154     if (root instanceof CalculatedExpressionNode)
155     {
156       pushDown((CalculatedExpressionNode) root, ".");
157       pushDown((CalculatedExpressionNode) root, "/");
158       pushDown((CalculatedExpressionNode) root, "*");
159       pushDown((CalculatedExpressionNode) root, "%");
160       pushDown((CalculatedExpressionNode) root, "+-");
161       pushDown((CalculatedExpressionNode) root, "like");
162     }
163   }
164
165   private void normalizeAndOr(SimpleNode root)
166   {
167     for (int i = 0; i < root.getChildCount(); i++)
168     {
169       normalizeAndOr(root.getChild(i));
170     }
171
172     if (root instanceof ExpressionNode)
173     {
174       pushDown((ExpressionNode) root, "&&");
175       pushDown((ExpressionNode) root, "||");
176
177     }
178   }
179
180   private boolean pruneCalculatedExpressions(SimpleNode root) throws ParseException
181   {
182     boolean doneOne = false;
183
184     int i = 0;
185     while (i < root.getChildCount())
186     {
187       if (!pruneCalculatedExpressions(root.getChild(i))) i++;
188     }
189
190     if (root instanceof CalculatedExpressionNode)
191     {
192       SimpleNode parent = root.getParent();
193       if (root.getChildCount() != 1)
194       {
195         throw new ParseException("Calculated expression with childcount != 1 found", parent.beginLine,
196             parent.beginColumn);
197       }
198       root.getChild(0).increaseCloseBracket(root.getBracketCloseCount());
199       root.getChild(0).increaseOpenBracket(root.getBracketOpenCount());
200       parent.replaceChild(root, root.getChild(0));
201       doneOne = true;
202     }
203     return doneOne;
204   }
205
206   private void pruneUnary(SimpleNode root) throws ParseException
207   {
208     int i = 0;
209     while (i < root.getChildCount())
210     {
211       int increment = 1;
212       if (root.getChild(i) instanceof ExpressionNode)
213       {
214         ExpressionNode exprNode = (ExpressionNode) root.getChild(i);
215         if (exprNode.getChildCount() != 1) throw new ParseException("Expression (" + exprNode.toString()
216                                                                     + ") with more than 1 child found",
217             exprNode.beginLine, exprNode.beginColumn);
218
219         SimpleNode child = exprNode.getChild(0);
220
221         child.increaseCloseBracket(root.getChild(i).getBracketCloseCount());
222         child.increaseOpenBracket(root.getChild(i).getBracketOpenCount());
223
224         root.replaceChild(i, child);
225         increment = 0;
226       }
227       if (root.getChild(i) instanceof SubExpressionNode)
228       {
229         SubExpressionNode exprNode = (SubExpressionNode) root.getChild(i);
230         if (exprNode.isUnary())
231         {
232           SimpleNode child = exprNode.getChild(0);
233
234           child.increaseCloseBracket(root.getChild(i).getBracketCloseCount());
235           child.increaseOpenBracket(root.getChild(i).getBracketOpenCount());
236
237           root.replaceChild(i, child);
238           increment = 0;
239         }
240       }
241       i += increment;
242     }
243
244     for (int j = 0; j < root.getChildCount(); j++)
245     {
246       pruneUnary(root.getChild(j));
247     }
248   }
249
250 }
Popular Tags