/** * OTN needs to override remove to avoid releasing the node ID, since OTN are never removed from * the rulebase in the current implementation */ protected void doRemove( final RuleRemovalContext context, final ReteooBuilder builder, final BaseNode node, final InternalWorkingMemory[] workingMemories) { if (context.getCleanupAdapter() != null) { for (InternalWorkingMemory workingMemory : workingMemories) { CleanupAdapter adapter = context.getCleanupAdapter(); final ObjectHashSet memory = (ObjectHashSet) workingMemory.getNodeMemory(this); Iterator it = memory.iterator(); for (ObjectEntry entry = (ObjectEntry) it.next(); entry != null; entry = (ObjectEntry) it.next()) { InternalFactHandle handle = (InternalFactHandle) entry.getValue(); for (LeftTuple leftTuple = handle.getFirstLeftTuple(); leftTuple != null; leftTuple = leftTuple.getLeftParentNext()) { adapter.cleanUp(leftTuple, workingMemory); } } } context.setCleanupAdapter(null); } if (!node.isInUse()) { removeObjectSink((ObjectSink) node); } }
protected void doRemove( final RuleRemovalContext context, final ReteooBuilder builder, final BaseNode node, final InternalWorkingMemory[] workingMemories) { if (!node.isInUse()) { removeTupleSink((LeftTupleSink) node); } if (!this.isInUse() || context.getCleanupAdapter() != null) { for (InternalWorkingMemory workingMemory : workingMemories) { BetaMemory memory; Object object = workingMemory.getNodeMemory(this); // handle special cases for Accumulate to make sure they tidy up their specific data // like destroying the local FactHandles if (object instanceof AccumulateMemory) { memory = ((AccumulateMemory) object).betaMemory; } else { memory = (BetaMemory) object; } FastIterator it = memory.getLeftTupleMemory().fullFastIterator(); for (LeftTuple leftTuple = getFirstLeftTuple(memory.getLeftTupleMemory(), it); leftTuple != null; ) { LeftTuple tmp = (LeftTuple) it.next(leftTuple); if (context.getCleanupAdapter() != null) { LeftTuple child; while ((child = leftTuple.getFirstChild()) != null) { if (child.getLeftTupleSink() == this) { // this is a match tuple on collect and accumulate nodes, so just unlink it child.unlinkFromLeftParent(); child.unlinkFromRightParent(); } else { // the cleanupAdapter will take care of the unlinking context.getCleanupAdapter().cleanUp(child, workingMemory); } } } memory.getLeftTupleMemory().remove(leftTuple); leftTuple.unlinkFromLeftParent(); leftTuple.unlinkFromRightParent(); leftTuple = tmp; } // handle special cases for Accumulate to make sure they tidy up their specific data // like destroying the local FactHandles if (object instanceof AccumulateMemory) { ((AccumulateNode) this).doRemove(workingMemory, (AccumulateMemory) object); } if (!this.isInUse()) { it = memory.getRightTupleMemory().fullFastIterator(); for (RightTuple rightTuple = getFirstRightTuple(memory.getRightTupleMemory(), it); rightTuple != null; ) { RightTuple tmp = (RightTuple) it.next(rightTuple); if (rightTuple.getBlocked() != null) { // special case for a not, so unlink left tuple from here, as they aren't in the left // memory for (LeftTuple leftTuple = rightTuple.getBlocked(); leftTuple != null; ) { LeftTuple temp = leftTuple.getBlockedNext(); leftTuple.setBlocker(null); leftTuple.setBlockedPrevious(null); leftTuple.setBlockedNext(null); leftTuple.unlinkFromLeftParent(); leftTuple = temp; } } memory.getRightTupleMemory().remove(rightTuple); rightTuple.unlinkFromRightParent(); rightTuple = tmp; } workingMemory.clearNodeMemory(this); } } context.setCleanupAdapter(null); } this.rightInput.remove(context, builder, this, workingMemories); this.leftInput.remove(context, builder, this, workingMemories); }