1 13 package com.tonbeller.jpivot.olap.query; 14 15 import java.util.ArrayList ; 16 import java.util.Iterator ; 17 import java.util.List ; 18 19 import com.tonbeller.jpivot.olap.model.Hierarchy; 20 import com.tonbeller.jpivot.util.TreeNode; 21 22 25 public class ExpGenerator { 26 27 TreeNode rootNode = null; 28 int nDimension; 29 Hierarchy[] hiers; 30 31 QuaxUti uti; 32 33 36 public ExpGenerator(QuaxUti uti) { 37 this.uti = uti; 38 } 39 40 43 public void init(TreeNode rootNode, Hierarchy[] hiers) { 44 this.rootNode = rootNode; 45 this.hiers = hiers; 46 this.nDimension = hiers.length; 47 } 48 49 54 public Object genExp() { 55 56 Object exp = null; 57 List nodes = rootNode.getChildren(); 58 59 List openSet = new ArrayList (); NodeLoop: for (Iterator iter = nodes.iterator(); iter.hasNext();) { 63 TreeNode node = (TreeNode) iter.next(); 64 Object expForNode = null; 65 expForNode = genExpForNode(node, nDimension); 66 boolean closeOpenSet = false; 67 if (nDimension == 1) { 68 if (uti.isMember(expForNode)) { 69 openSet.add(expForNode); 70 continue NodeLoop; 71 } else 72 closeOpenSet = true; 73 } else { 74 if (uti.isFunCallTo(expForNode, "()")) { 75 openSet.add(expForNode); 76 continue NodeLoop; 77 } else 78 closeOpenSet = true; 79 } 80 81 if (closeOpenSet && openSet.size() > 0) { 82 Object [] expArray = openSet.toArray(new Object [0]); 84 Object set = uti.createFunCall("{}", expArray, QuaxUti.FUNTYPE_BRACES); 85 if (exp == null) { 86 exp = set; 87 } else { 88 exp = uti.createFunCall("Union", new Object [] { exp, set }, QuaxUti.FUNTYPE_FUNCTION); 90 } 91 openSet.clear(); 92 } 93 94 if (exp == null) { 95 exp = expForNode; 96 } else { 97 exp = uti 99 .createFunCall("Union", new Object [] { exp, expForNode }, QuaxUti.FUNTYPE_FUNCTION); 100 } 101 } 102 if (openSet.size() > 0) { 103 Object [] expArray = openSet.toArray(new Object [0]); 105 Object set = uti.createFunCall("{}", expArray, QuaxUti.FUNTYPE_BRACES); 106 if (exp == null) { 107 exp = set; 108 } else { 109 exp = uti.createFunCall("Union", new Object [] { exp, set }, QuaxUti.FUNTYPE_FUNCTION); 111 } 112 openSet.clear(); 113 } 114 115 return exp; 116 } 117 118 124 private Object genExpForNode(TreeNode node, int untilIndex) { 125 126 Object eNode = node.getReference(); 127 if (node.getLevel() == untilIndex) 128 return eNode; 130 Object [] tuple = genTuple(node); 132 if (tuple != null) { 133 if (tuple.length == 1) 134 return tuple[0]; 135 else 136 return uti.createFunCall("()", tuple, QuaxUti.FUNTYPE_TUPLE); 137 } 138 139 Object exp = null; 141 List childNodes = node.getChildren(); 142 for (Iterator iter = childNodes.iterator(); iter.hasNext();) { 143 TreeNode childNode = (TreeNode) iter.next(); 144 Object childExp = genExpForNode(childNode, untilIndex); 145 Object childSet = bracesAround(childExp); 146 147 Object eSet; 148 if (!uti.isMember(eNode)) { 149 eSet = eNode; 151 } else { 152 eSet = uti.createFunCall("{}", new Object [] { eNode }, QuaxUti.FUNTYPE_BRACES); 154 } 155 Object cj = uti.createFunCall("CrossJoin", new Object [] { eSet, childSet }, 156 QuaxUti.FUNTYPE_FUNCTION); 157 if (exp == null) 158 exp = cj; 159 else { 160 exp = uti.createFunCall("Union", new Object [] { exp, cj }, QuaxUti.FUNTYPE_FUNCTION); 161 } 162 } 163 return exp; 164 } 165 166 172 private Object genUnion(Object [] oExps) { 173 if (oExps.length == 1) 174 return oExps[0]; 175 Object oUnion = uti.createFunCall("Union", new Object [] { oExps[0], oExps[1] }, 176 QuaxUti.FUNTYPE_FUNCTION); 177 for (int i = 2; i < oExps.length; i++) 178 oUnion = uti.createFunCall("Union", new Object [] { oUnion, oExps[i] }, 179 QuaxUti.FUNTYPE_FUNCTION); 180 return oUnion; 181 } 182 183 189 private Object bracesAround(Object oExp) { 190 Object oSet; 191 if (uti.isMember(oExp) || uti.isFunCallTo(oExp, "()")) 192 oSet = uti.createFunCall("{}", new Object [] { oExp }, QuaxUti.FUNTYPE_BRACES); 193 else 194 oSet = oExp; 195 return oSet; 196 } 197 198 204 private Object [] genTuple(TreeNode node) { 205 if (!uti.isMember(node.getReference())) 206 return null; 207 int size = nDimension - node.getLevel() + 1; 208 if (size == 1) { 209 return new Object [] { node.getReference() }; } 211 List childNodes = node.getChildren(); 212 if (childNodes.size() != 1) 213 return null; 214 Object [] nextTuple = genTuple((TreeNode) childNodes.get(0)); 215 if (nextTuple == null) 216 return null; 217 Object [] tupleMembers = new Object [size]; 218 tupleMembers[0] = node.getReference(); 219 for (int i = 1; i < tupleMembers.length; i++) { 220 tupleMembers[i] = nextTuple[i - 1]; 221 } 222 return tupleMembers; 223 } 224 225 } | Popular Tags |