@Override protected void loadRight() throws TeiidComponentException, TeiidProcessingException { if (this.joinNode.getJoinType() != JoinType.JOIN_FULL_OUTER || this.joinNode.getJoinCriteria() == null) { this.rightSource.setImplicitBuffer(ImplicitBuffer.ON_MARK); } this.rightSource.sort(this.processingSortRight); }
private void declineSort() { RelationalNode parent = this.getParent(); RelationalNode child = this; while (parent != null && !(parent instanceof JoinNode)) { child = parent; parent = parent.getParent(); } if (parent != null) { JoinNode joinNode = (JoinNode)parent; if (joinNode.getJoinStrategy() instanceof MergeJoinStrategy) { MergeJoinStrategy mjs = (MergeJoinStrategy)joinNode.getJoinStrategy(); if (joinNode.getChildren()[0] == child) { mjs.setProcessingSortLeft(true); } else { mjs.setProcessingSortRight(true); } } } sort = false; }
public void initialize(JoinNode joinNode) { this.joinNode = joinNode; this.leftSource = new SourceState(joinNode.getChildren()[0], joinNode.getLeftExpressions()); this.leftSource.markExpressionsDistinct(this.joinNode.isLeftDistinct()); this.rightSource = new SourceState(joinNode.getChildren()[1], joinNode.getRightExpressions()); this.rightSource.markExpressionsDistinct(this.joinNode.isRightDistinct()); }
public TupleBatch nextBatchDirect() throws TeiidComponentException, TeiidProcessingException { CommandContext context = getContext(); if (!isDependent()) { boolean old = context.setParallel(true); try { return nextBatchDirectInternal(); } finally { context.setParallel(old); } } return nextBatchDirectInternal(); }
public void open() throws TeiidComponentException, TeiidProcessingException { CommandContext context = getContext(); if (!isDependent()) { boolean old = context.setParallel(true); try { openInternal(); } finally { context.setParallel(old); } } else { openInternal(); } }
JoinNode jnode = new JoinNode(getID()); jnode.setJoinType(jtype); jnode.setLeftDistinct(node.hasBooleanProperty(NodeConstants.Info.IS_LEFT_DISTINCT)); jnode.setRightDistinct(node.hasBooleanProperty(NodeConstants.Info.IS_RIGHT_DISTINCT)); List joinCrits = (List) node.getProperty(NodeConstants.Info.JOIN_CRITERIA); String depValueSource = (String) node.getProperty(NodeConstants.Info.DEPENDENT_VALUE_SOURCE); jnode.setJoinStrategy(mjStrategy); List leftExpressions = (List) node.getProperty(NodeConstants.Info.LEFT_EXPRESSIONS); List rightExpressions = (List) node.getProperty(NodeConstants.Info.RIGHT_EXPRESSIONS); jnode.setJoinExpressions(leftExpressions, rightExpressions); joinCrits = (List) node.getProperty(NodeConstants.Info.NON_EQUI_JOIN_CRITERIA); } else if (stype == JoinStrategyType.NESTED_TABLE) { NestedTableJoinStrategy ntjStrategy = new NestedTableJoinStrategy(); jnode.setJoinStrategy(ntjStrategy); SymbolMap references = (SymbolMap)node.getProperty(Info.LEFT_NESTED_REFERENCES); ntjStrategy.setLeftMap(references); } else { NestedLoopJoinStrategy nljStrategy = new NestedLoopJoinStrategy(); jnode.setJoinStrategy(nljStrategy); jnode.setJoinCriteria(joinCrit); jnode.setDependentValueSource(depValueSource); JoinNode joinAsSet = new JoinNode(getID()); joinAsSet.setJoinStrategy(new MergeJoinStrategy(SortOption.SORT_DISTINCT, SortOption.SORT_DISTINCT, true));
if (isDependent() && (this.joinType == JoinType.JOIN_ANTI_SEMI || this.joinType == JoinType.JOIN_SEMI)) { rightDep = true; this.joinStrategy.openRight(); this.getContext().getVariableContext().setGlobalValue(this.dependentValueSource, dvs); if (this.joinType != JoinType.JOIN_FULL_OUTER || this.getJoinCriteria() == null) { this.joinStrategy.leftSource.setImplicitBuffer(ImplicitBuffer.NONE); if (isDependent() && !rightDep) { TupleBuffer buffer = this.joinStrategy.leftSource.getTupleBuffer(); this.getContext().getVariableContext().setGlobalValue(this.dependentValueSource, dvs); if (!isDependent()) { if (getJoinType() != JoinType.JOIN_FULL_OUTER && this.joinStrategy.leftSource.getSortUtility() == null && this.joinStrategy.leftSource.rowCountLE(0)) { this.terminateBatches(); return pullBatch(); prefetch(this.joinStrategy.rightSource, this.joinStrategy.leftSource); if (getJoinType() != JoinType.JOIN_FULL_OUTER && this.joinStrategy.leftSource.getSortUtility() == null && this.joinStrategy.leftSource.rowCountLE(0)) { this.terminateBatches(); return pullBatch(); this.terminateBatches(); } catch (BatchAvailableException e) { prefetch(this.joinStrategy.leftSource, this.joinStrategy.rightSource);
joinStrategy = new MergeJoinStrategy(SortOption.SORT_DISTINCT, SortOption.SORT_DISTINCT, false); join = new JoinNode(3); join.setElements(joinElements); join.setJoinType(joinType); join.setJoinExpressions(Arrays.asList(es1), Arrays.asList(es3)); join.setJoinStrategy(joinStrategy);
/** * @see org.teiid.query.processor.relational.RelationalNode#getNodeString(java.lang.StringBuffer) * @since 4.2 */ protected void getNodeString(StringBuffer str) { str.append(getClassName()); str.append("("); //$NON-NLS-1$ str.append(getID()); str.append(") [");//$NON-NLS-1$ if(isDependent()) { str.append("Dependent] [");//$NON-NLS-1$ } str.append(this.joinStrategy.toString()); str.append("] [");//$NON-NLS-1$ str.append(this.joinType.toString()); str.append("]"); //$NON-NLS-1$ if (getJoinType() != JoinType.JOIN_CROSS) { str.append(" criteria=").append(getCriteriaList()); //$NON-NLS-1$ } str.append(" output="); //$NON-NLS-1$ str.append(getElements()); }
if (processingSortRight == SortOption.SORT && this.joinNode.getJoinType() != JoinType.JOIN_LEFT_OUTER && shouldIndexIfSmall(this.leftSource)) { this.processingSortRight = SortOption.NOT_SORTED; } else if (!this.leftSource.hasBuffer() && processingSortLeft == SortOption.SORT && shouldIndexIfSmall(this.rightSource)) { this.processingSortLeft = SortOption.NOT_SORTED; } else { if (!this.rightSource.hasBuffer() && processingSortRight == SortOption.SORT && this.joinNode.getJoinType() != JoinType.JOIN_LEFT_OUTER && shouldIndexIfSmall(this.leftSource)) { this.processingSortRight = SortOption.NOT_SORTED; } else if (processingSortRight == SortOption.SORT && this.joinNode.getJoinType() != JoinType.JOIN_LEFT_OUTER && ((!this.rightSource.hasBuffer() && processingSortLeft != SortOption.SORT) || shouldIndex(this.leftSource, this.rightSource))) { this.processingSortRight = SortOption.NOT_SORTED; } else if (processingSortLeft == SortOption.SORT && shouldIndex(this.rightSource, this.leftSource)) { RelationalNode parent = this.joinNode.getParent(); boolean hasLimit = false; while (parent != null && !hasLimit) { if (hasLimit && this.joinNode.getJoinType() != JoinType.JOIN_LEFT_OUTER) { super.loadLeft(); if (LogManager.isMessageToBeRecorded(LogConstants.CTX_DQP, MessageLevel.DETAIL)) { LogManager.logDetail(LogConstants.CTX_DQP, "degrading to merged join", this.joinNode.getID()); //$NON-NLS-1$ this.notSortedSource.sort(SortOption.NOT_SORTED); //do a single sort pass if (LogManager.isMessageToBeRecorded(LogConstants.CTX_DQP, MessageLevel.DETAIL)) { LogManager.logDetail(LogConstants.CTX_DQP, "performing single pass sort right", this.joinNode.getID()); //$NON-NLS-1$ if (!this.joinNode.getDependentValueSource().isUnused()) { this.notSortedSource.sort(SortOption.NOT_SORTED); //do a single sort pass if (LogManager.isMessageToBeRecorded(LogConstants.CTX_DQP, MessageLevel.DETAIL)) {
} else { this.leftScanState = ScanState.DONE; if (joinNode.getJoinType() != JoinType.JOIN_FULL_OUTER) { mergeState = MergeState.DONE; return; } else { this.rightScanState = ScanState.DONE; if (!this.joinNode.getJoinType().isOuter()) { mergeState = MergeState.DONE; return; } else if (result > 0) { this.leftScanState = ScanState.READ; if (this.joinNode.getJoinType().isOuter()) { this.joinNode.addBatchRow(outputTuple(this.leftSource.getCurrentTuple(), this.rightSource.getOuterVals())); if (joinNode.getJoinType() == JoinType.JOIN_FULL_OUTER) { this.joinNode.addBatchRow(outputTuple(this.leftSource.getOuterVals(), this.rightSource.getCurrentTuple())); innerState.reset(); loopState = LoopState.LOAD_INNER; } else if (matchState == MatchState.MATCH_LEFT && joinNode.getJoinType() == JoinType.JOIN_FULL_OUTER && this.joinNode.getJoinCriteria() != null) { boolean match = this.joinNode.matchesCriteria(outputTuple); if (matchState == MatchState.MATCH_LEFT && this.joinNode.getJoinType() != JoinType.JOIN_ANTI_SEMI) { if (this.joinNode.getJoinType() == JoinType.JOIN_SEMI) { this.loopState = LoopState.LOAD_OUTER; //only one match is needed for semi join
joinNode.getContext().getVariableContext().setValue(entry.getKey(), eval.evaluate(entry.getValue(), null)); boolean matches = this.joinNode.matchesCriteria(outputTuple); joinNode.addBatchRow(outputTuple); if (!outerMatched && this.joinNode.getJoinType() == JoinType.JOIN_LEFT_OUTER) { joinNode.addBatchRow(outputTuple(this.leftSource.getCurrentTuple(), this.rightSource.getOuterVals())); rightSource.close(); for (Map.Entry<ElementSymbol, Expression> entry : rightMap.asMap().entrySet()) { joinNode.getContext().getVariableContext().remove(entry.getKey());
Class<?> nodeType = relationalNode.getClass(); if(nodeType.equals(JoinNode.class)) { JoinStrategy strategy = ((JoinNode)relationalNode).getJoinStrategy(); if (((JoinNode)relationalNode).getJoinType().equals(JoinType.JOIN_SEMI)) { updateCounts(SemiJoin.class, counts, types); } else if (((JoinNode)relationalNode).getJoinType().equals(JoinType.JOIN_ANTI_SEMI)) { updateCounts(AntiSemiJoin.class, counts, types); updateCounts(NestedTableJoinStrategy.class, counts, types); if (((JoinNode)relationalNode).isDependent()) { updateCounts(DependentJoin.class, counts, types);
private boolean shouldIndex(SourceState possibleIndex, SourceState other) throws TeiidComponentException, TeiidProcessingException { long size = joinNode.getBatchSize(); long indexSize = possibleIndex.hasBuffer()?possibleIndex.getRowCount():-1; long otherSize = other.hasBuffer()?other.getRowCount():-1; int schemaSize = this.joinNode.getBufferManager().getSchemaSize(other.getSource().getOutputElements()); int toReserve = this.joinNode.getBufferManager().getMaxProcessingSize(); int minSize = toReserve/schemaSize*this.joinNode.getBatchSize(); if (otherSize != -1 && otherSize < this.joinNode.getBatchSize()) { if (other.hasBuffer() && ((other.getRowCount() <= this.joinNode.getBatchSize()) || (possibleIndex.getRowCount() > this.joinNode.getBatchSize() && other.rowCountLE(minSize)))) { return false; //just use a merge join int indexSchemaSize = this.joinNode.getBufferManager().getSchemaSize(possibleIndex.getSource().getOutputElements()); if (toReserve < this.joinNode.getBufferManager().getMaxProcessingSize()) { useIndex = true; } else if (possibleIndex.getRowCount() / this.joinNode.getBatchSize() < preferMemCutoff) { useIndex = true; reserved += this.joinNode.getBufferManager().reserveBuffers(toReserve, BufferReserveMode.FORCE); if (other.hasBuffer()) { other.getTupleBuffer().setForwardOnly(true); if (joinNode.getJoinType() == JoinType.JOIN_LEFT_OUTER) { return false; //repeated is not supported as it could produce multiple outer matches
return; if (this.sortedSource.getRowCount() == 0 && joinNode.getJoinType() != JoinType.JOIN_LEFT_OUTER) { return; if (this.sortedSource.getRowCount() == 0 && joinNode.getJoinType() == JoinType.JOIN_LEFT_OUTER) { outerMatch(); continue; List<?> tuple = this.currentTuple; this.currentTuple = null; this.joinNode.addBatchRow(outputTuple(this.leftSource.getOuterVals(), tuple)); continue; List outputTuple = outputTuple(this.processingSortLeft==SortOption.NOT_SORTED?currentTuple:reorderedTuple, this.processingSortLeft==SortOption.NOT_SORTED?reorderedTuple:currentTuple); boolean matches = this.joinNode.matchesCriteria(outputTuple); this.sortedTuple = null; if (matches) { matched = true; this.joinNode.addBatchRow(outputTuple);
IndexedTupleSource its = state.getTupleBuffer().createIndexedTupleSource(!joinNode.isDependent()); boolean sorted = sortOption == SortOption.ALREADY_SORTED; int[] expressionIndexes = state.getExpressionIndexes(); keyLength++; index = this.joinNode.getBufferManager().createSTree(reordered, this.joinNode.getConnectionID(), keyLength); index.setPreferMemory(true); if (sortOption == SortOption.SORT_DISTINCT) {
helpCreateJoin(); this.joinStrategy = new EnhancedSortMergeJoinStrategy(SortOption.SORT, SortOption.SORT); this.join.setJoinStrategy(joinStrategy);
private void outerMatch() { List<?> tuple = currentTuple; currentTuple = null; if (!matched && joinNode.getJoinType() == JoinType.JOIN_LEFT_OUTER) { this.joinNode.addBatchRow(outputTuple(tuple, this.rightSource.getOuterVals())); } }
/** * @see org.teiid.query.processor.relational.RelationalNode#getDescriptionProperties() * @since 4.2 */ public PlanNode getDescriptionProperties() { // Default implementation - should be overridden PlanNode props = super.getDescriptionProperties(); if(isDependent()) { props.addProperty(PROP_DEPENDENT, Boolean.TRUE.toString()); } props.addProperty(PROP_JOIN_STRATEGY, this.joinStrategy.toString()); props.addProperty(PROP_JOIN_TYPE, this.joinType.toString()); List<String> critList = getCriteriaList(); props.addProperty(PROP_JOIN_CRITERIA, critList); return props; }
@Override protected void loadLeft() throws TeiidComponentException, TeiidProcessingException { if (this.joinNode.isDependent()) { this.leftSource.getTupleBuffer(); } }