1 21 22 package org.apache.derby.impl.sql.compile; 23 24 import org.apache.derby.iapi.sql.compile.CostEstimate; 25 import org.apache.derby.iapi.sql.compile.ExpressionClassBuilderInterface; 26 import org.apache.derby.iapi.sql.compile.JoinStrategy; 27 import org.apache.derby.iapi.sql.compile.Optimizable; 28 import org.apache.derby.iapi.sql.compile.Optimizer; 29 import org.apache.derby.iapi.sql.compile.OptimizablePredicateList; 30 import org.apache.derby.iapi.sql.compile.OptimizablePredicate; 31 32 import org.apache.derby.iapi.sql.dictionary.DataDictionary; 33 import org.apache.derby.iapi.sql.dictionary.ConglomerateDescriptor; 34 35 import org.apache.derby.iapi.store.access.StoreCostController; 36 import org.apache.derby.iapi.store.access.TransactionController; 37 38 import org.apache.derby.iapi.services.compiler.MethodBuilder; 39 40 import org.apache.derby.impl.sql.compile.ExpressionClassBuilder; 41 42 import org.apache.derby.iapi.error.StandardException; 43 44 import org.apache.derby.iapi.services.sanity.SanityManager; 45 46 public class NestedLoopJoinStrategy extends BaseJoinStrategy { 47 public NestedLoopJoinStrategy() { 48 } 49 50 51 56 public boolean feasible(Optimizable innerTable, 57 OptimizablePredicateList predList, 58 Optimizer optimizer 59 ) 60 throws StandardException 61 { 62 75 if (innerTable.isMaterializable()) 76 { 77 return true; 78 } 79 if (innerTable.supportsMultipleInstantiations()) 80 { 81 return true; 82 } 83 return false; 84 } 85 86 87 public boolean multiplyBaseCostByOuterRows() { 88 return true; 89 } 90 91 96 public OptimizablePredicateList getBasePredicates( 97 OptimizablePredicateList predList, 98 OptimizablePredicateList basePredicates, 99 Optimizable innerTable) 100 throws StandardException { 101 if (SanityManager.DEBUG) { 102 SanityManager.ASSERT(basePredicates == null || 103 basePredicates.size() == 0, 104 "The base predicate list should be empty."); 105 } 106 107 if (predList != null) { 108 predList.transferAllPredicates(basePredicates); 109 basePredicates.classify(innerTable, 110 innerTable.getCurrentAccessPath().getConglomerateDescriptor()); 111 } 112 113 return basePredicates; 114 } 115 116 117 public double nonBasePredicateSelectivity( 118 Optimizable innerTable, 119 OptimizablePredicateList predList) { 120 124 return 1.0; 125 } 126 127 132 public void putBasePredicates(OptimizablePredicateList predList, 133 OptimizablePredicateList basePredicates) 134 throws StandardException { 135 for (int i = basePredicates.size() - 1; i >= 0; i--) { 136 OptimizablePredicate pred = basePredicates.getOptPredicate(i); 137 138 predList.addOptPredicate(pred); 139 basePredicates.removeOptPredicate(i); 140 } 141 } 142 143 144 public void estimateCost(Optimizable innerTable, 145 OptimizablePredicateList predList, 146 ConglomerateDescriptor cd, 147 CostEstimate outerCost, 148 Optimizer optimizer, 149 CostEstimate costEstimate) { 150 costEstimate.multiply(outerCost.rowCount(), costEstimate); 151 152 optimizer.trace(Optimizer.COST_OF_N_SCANS, innerTable.getTableNumber(), 0, outerCost.rowCount(), 153 costEstimate); 154 } 155 156 157 public int maxCapacity( int userSpecifiedCapacity, 158 int maxMemoryPerTable, 159 double perRowUsage) { 160 return Integer.MAX_VALUE; 161 } 162 163 164 public String getName() { 165 return "NESTEDLOOP"; 166 } 167 168 169 public int scanCostType() { 170 return StoreCostController.STORECOST_SCAN_NORMAL; 171 } 172 173 174 public String resultSetMethodName(boolean bulkFetch) { 175 if (bulkFetch) 176 return "getBulkTableScanResultSet"; 177 else 178 return "getTableScanResultSet"; 179 } 180 181 182 public String joinResultSetMethodName() { 183 return "getNestedLoopJoinResultSet"; 184 } 185 186 187 public String halfOuterJoinResultSetMethodName() { 188 return "getNestedLoopLeftOuterJoinResultSet"; 189 } 190 191 196 public int getScanArgs( 197 TransactionController tc, 198 MethodBuilder mb, 199 Optimizable innerTable, 200 OptimizablePredicateList storeRestrictionList, 201 OptimizablePredicateList nonStoreRestrictionList, 202 ExpressionClassBuilderInterface acbi, 203 int bulkFetch, 204 MethodBuilder resultRowAllocator, 205 int colRefItem, 206 int indexColItem, 207 int lockMode, 208 boolean tableLocked, 209 int isolationLevel, 210 int maxMemoryPerTable 211 ) 212 throws StandardException { 213 ExpressionClassBuilder acb = (ExpressionClassBuilder) acbi; 214 int numArgs; 215 216 if (SanityManager.DEBUG) { 217 if (nonStoreRestrictionList.size() != 0) { 218 SanityManager.THROWASSERT( 219 "nonStoreRestrictionList should be empty for " + 220 "nested loop join strategy, but it contains " + 221 nonStoreRestrictionList.size() + 222 " elements"); 223 } 224 } 225 226 if (bulkFetch > 1) 227 { 228 numArgs = 25; 229 } 230 else 231 { 232 numArgs = 24 ; 233 } 234 235 fillInScanArgs1(tc, mb, 236 innerTable, 237 storeRestrictionList, 238 acb, 239 resultRowAllocator); 240 241 fillInScanArgs2(mb, 242 innerTable, 243 bulkFetch, 244 colRefItem, 245 indexColItem, 246 lockMode, 247 tableLocked, 248 isolationLevel); 249 250 return numArgs; 251 } 252 253 258 public void divideUpPredicateLists( 259 Optimizable innerTable, 260 OptimizablePredicateList originalRestrictionList, 261 OptimizablePredicateList storeRestrictionList, 262 OptimizablePredicateList nonStoreRestrictionList, 263 OptimizablePredicateList requalificationRestrictionList, 264 DataDictionary dd 265 ) throws StandardException 266 { 267 271 originalRestrictionList.setPredicatesAndProperties(storeRestrictionList); 272 } 273 274 277 public boolean doesMaterialization() 278 { 279 return false; 280 } 281 282 public String toString() { 283 return getName(); 284 } 285 286 293 protected boolean validForOutermostTable() 294 { 295 return true; 296 } 297 } 298 | Popular Tags |