⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 projectrestrictnode.java

📁 derby database source code.good for you.
💻 JAVA
📖 第 1 页 / 共 4 页
字号:
/*   Derby - Class org.apache.derby.impl.sql.compile.ProjectRestrictNode   Copyright 1997, 2004 The Apache Software Foundation or its licensors, as applicable.   Licensed under the Apache License, Version 2.0 (the "License");   you may not use this file except in compliance with the License.   You may obtain a copy of the License at      http://www.apache.org/licenses/LICENSE-2.0   Unless required by applicable law or agreed to in writing, software   distributed under the License is distributed on an "AS IS" BASIS,   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.   See the License for the specific language governing permissions and   limitations under the License. */package	org.apache.derby.impl.sql.compile;import org.apache.derby.iapi.services.context.ContextManager;import org.apache.derby.iapi.sql.compile.Optimizable;import org.apache.derby.iapi.sql.compile.OptimizablePredicate;import org.apache.derby.iapi.sql.compile.OptimizablePredicateList;import org.apache.derby.iapi.sql.compile.Optimizer;import org.apache.derby.iapi.sql.compile.CostEstimate;import org.apache.derby.iapi.sql.compile.OptimizableList;import org.apache.derby.iapi.sql.compile.Visitable;import org.apache.derby.iapi.sql.compile.Visitor;import org.apache.derby.iapi.sql.compile.RequiredRowOrdering;import org.apache.derby.iapi.sql.compile.RowOrdering;import org.apache.derby.iapi.sql.compile.AccessPath;import org.apache.derby.iapi.sql.compile.C_NodeTypes;import org.apache.derby.iapi.sql.dictionary.DataDictionary;import org.apache.derby.iapi.sql.dictionary.ConglomerateDescriptor;import org.apache.derby.iapi.types.DataValueDescriptor;import org.apache.derby.iapi.sql.execute.NoPutResultSet;import org.apache.derby.iapi.sql.Activation;import org.apache.derby.iapi.sql.ResultSet;import org.apache.derby.iapi.error.StandardException;import org.apache.derby.iapi.reference.ClassName;import org.apache.derby.iapi.store.access.TransactionController;import org.apache.derby.impl.sql.compile.ExpressionClassBuilder;import org.apache.derby.impl.sql.compile.ActivationClassBuilder;import org.apache.derby.iapi.services.compiler.MethodBuilder;import org.apache.derby.iapi.services.loader.GeneratedMethod;import org.apache.derby.iapi.services.sanity.SanityManager;import org.apache.derby.catalog.types.ReferencedColumnsDescriptorImpl;import org.apache.derby.iapi.util.JBitSet;import org.apache.derby.iapi.services.classfile.VMOpcode;import java.util.Properties;import java.util.HashSet;import java.util.Set;/** * A ProjectRestrictNode represents a result set for any of the basic DML * operations: SELECT, INSERT, UPDATE, and DELETE.  For INSERT with * a VALUES clause, restriction will be null. For both INSERT and UPDATE, * the resultColumns in the selectList will contain the names of the columns * being inserted into or updated. * * NOTE: A ProjectRestrictNode extends FromTable since it can exist in a FromList. * * @author Jeff Lichtman */public class ProjectRestrictNode extends SingleChildResultSetNode{	/**	 * The ValueNode for the restriction to be evaluated here.	 */	public ValueNode	restriction;	/**	 * Constant expressions to be evaluated here.	 */	ValueNode	constantRestriction = null;	/**	 * Restriction as a PredicateList	 */	public PredicateList restrictionList;	/**	 * List of subqueries in projection	 */	SubqueryList projectSubquerys;	/**	 * List of subqueries in restriction	 */	SubqueryList restrictSubquerys;	private boolean accessPathModified;	private boolean accessPathConsidered;	private boolean childResultOptimized;	private boolean materialize;	/* Should we get the table number from this node,	 * regardless of the class of our child.	 */	private boolean getTableNumberHere;	/**	 * Initializer for a ProjectRestrictNode.	 *	 * @param childResult	The child ResultSetNode	 * @param projection	The result column list for the projection	 * @param restriction	An expression representing the restriction to be 	 *					    evaluated here.	 * @param restrictionList Restriction as a PredicateList	 * @param projectSubquerys List of subqueries in the projection	 * @param restrictSubquerys List of subqueries in the restriction	 * @param tableProperties	Properties list associated with the table	 */	public void init(							Object childResult,			 				Object projection,							Object restriction,							Object restrictionList,							Object projectSubquerys,							Object restrictSubquerys,							Object tableProperties)	{		super.init(childResult, tableProperties);		resultColumns = (ResultColumnList) projection;		this.restriction = (ValueNode) restriction;		this.restrictionList = (PredicateList) restrictionList;		this.projectSubquerys = (SubqueryList) projectSubquerys;		this.restrictSubquerys = (SubqueryList) restrictSubquerys;		/* A PRN will only hold the tableProperties for		 * a result set tree if its child is not an		 * optimizable.  Otherwise, the properties will		 * be transferred down to the child.		 */		if (tableProperties != null &&			 (childResult instanceof Optimizable))		{			((Optimizable) childResult).setProperties(getProperties());			setProperties((Properties) null);		}	}	/*	 *  Optimizable interface	 */	/**		@see Optimizable#nextAccessPath		@exception StandardException	Thrown on error	 */	public boolean nextAccessPath(Optimizer optimizer,									OptimizablePredicateList predList,									RowOrdering rowOrdering)			throws StandardException	{		/*		** If the child result set is an optimizable, let it choose its next		** access path.  If it is not an optimizable, we have to tell the		** caller that there is an access path the first time we are called		** for this position in the join order, and that there are no more		** access paths for subsequent calls for this position in the join		** order.  The startOptimizing() method is called once on each		** optimizable when it is put into a join position.		*/		if (childResult instanceof Optimizable)		{			return ((Optimizable) childResult).nextAccessPath(optimizer,																restrictionList,																rowOrdering);		}		else		{			return super.nextAccessPath(optimizer, predList, rowOrdering);		}	}	/** @see Optimizable#rememberAsBest 		@exception StandardException	Thrown on error	 */	public void rememberAsBest(int planType, Optimizer optimizer)		throws StandardException	{		super.rememberAsBest(planType, optimizer);		if (childResult instanceof Optimizable)			((Optimizable) childResult).rememberAsBest(planType, optimizer);	}	/* Don't print anything for a PRN, as their	 * child has the interesting info.	 */	void printRememberingBestAccessPath(int planType, AccessPath bestPath)	{	}	/** @see Optimizable#startOptimizing */	public void startOptimizing(Optimizer optimizer, RowOrdering rowOrdering)	{		if (childResult instanceof Optimizable)		{			((Optimizable) childResult).startOptimizing(optimizer, rowOrdering);		}		else		{			accessPathConsidered = false;			super.startOptimizing(optimizer, rowOrdering);		}	}	/** @see Optimizable#getTableNumber */	public int getTableNumber()	{		/* GROSS HACK - We need to get the tableNumber after		 * calling modifyAccessPaths() on the child when doing		 * a hash join on an arbitrary result set.  The problem		 * is that the child will always be an optimizable at this		 * point.  So, we 1st check to see if we should get it from		 * this node.  (We set the boolean to true in the appropriate		 * place in modifyAccessPaths().)		 */		if (getTableNumberHere)		{			return super.getTableNumber();		}		if (childResult instanceof Optimizable)			return ((Optimizable) childResult).getTableNumber();		return super.getTableNumber();	}	/**	 * @see Optimizable#optimizeIt	 *	 * @exception StandardException		Thrown on error	 */	public CostEstimate optimizeIt(							Optimizer optimizer,							OptimizablePredicateList predList,							CostEstimate outerCost,							RowOrdering rowOrdering)			throws StandardException	{		/*		** RESOLVE: Most types of Optimizables only implement estimateCost(),		** and leave it up to optimizeIt() in FromTable to figure out the		** total cost of the join.  A ProjectRestrict can have a non-Optimizable		** child, though, in which case we want to tell the child the		** number of outer rows - it could affect the join strategy		** significantly.  So we implement optimizeIt() here, which overrides		** the optimizeIt() in FromTable.  This assumes that the join strategy		** for which this join node is the inner table is a nested loop join,		** which will not be a valid assumption when we implement other		** strategies like materialization (hash join can work only on		** base tables).  The join strategy for a base table under a		** ProjectRestrict is set in the base table itself.		*/		CostEstimate childCost;		costEstimate = getCostEstimate(optimizer);		/*		** Don't re-optimize a child result set that has already been fully		** optimized.  For example, if the child result set is a SelectNode,		** it will be changed to a ProjectRestrictNode, which we don't want		** to re-optimized.		*/		// NOTE: TO GET THE RIGHT COST, THE CHILD RESULT MAY HAVE TO BE		// OPTIMIZED MORE THAN ONCE, BECAUSE THE NUMBER OF OUTER ROWS		// MAY BE DIFFERENT EACH TIME.		// if (childResultOptimized)		// 	return costEstimate;		// It's possible that a call to optimize the left/right will cause		// a new "truly the best" plan to be stored in the underlying base		// tables.  If that happens and then we decide to skip that plan		// (which we might do if the call to "considerCost()" below decides		// the current path is infeasible or not the best) we need to be		// able to revert back to the "truly the best" plans that we had		// saved before we got here.  So with this next call we save the		// current plans using "this" node as the key.  If needed, we'll		// then make the call to revert the plans in OptimizerImpl's		// getNextDecoratedPermutation() method.		addOrLoadBestPlanMapping(true, this);		/* If the childResult is instanceof Optimizable, then we optimizeIt.		 * Otherwise, we are going into a new query block.  If the new query		 * block has already had its access path modified, then there is		 * nothing to do.  Otherwise, we must begin the optimization process		 * anew on the new query block.		 */		if (childResult instanceof Optimizable)		{			childCost = ((Optimizable) childResult).optimizeIt(															optimizer,															restrictionList,															outerCost,															rowOrdering);			/* Copy child cost to this node's cost */			costEstimate.setCost(							childCost.getEstimatedCost(),							childCost.rowCount(),							childCost.singleScanRowCount());			// Note: we don't call "optimizer.considerCost()" here because			// a) the child will make that call as part of its own			// "optimizeIt()" work above, and b) the child might have			// different criteria for "considering" (i.e. rejecting or			// accepting) a plan's cost than this ProjectRestrictNode does--			// and we don't want to override the child's decision.  So as			// with most operations in this class, if the child is an			// Optimizable, we just let it do its own work and make its			// own decisions.		}		else if ( ! accessPathModified)		{			if (SanityManager.DEBUG)			{				if (! ((childResult instanceof SelectNode) ||								 (childResult instanceof RowResultSetNode)))				{					SanityManager.THROWASSERT(						"childResult is expected to be instanceof " +						"SelectNode or RowResultSetNode - it is a " +						childResult.getClass().getName());				}			}			childResult = childResult.optimize(optimizer.getDataDictionary(), 											   restrictionList,											   outerCost.rowCount());			/* Copy child cost to this node's cost */			childCost = childResult.costEstimate;			costEstimate.setCost(							childCost.getEstimatedCost(),							childCost.rowCount(),							childCost.singleScanRowCount());			getBestAccessPath().setCostEstimate(costEstimate);			/*			** The current access path may not be part of a sort avoidance			** path, but set the cost estimate there anyway, just in case			** it is.			*/			getBestSortAvoidancePath().setCostEstimate(costEstimate);			// childResultOptimized = true;			/* RESOLVE - ARBITRARYHASHJOIN - Passing restriction list here, as above, is correct.			 * However,  passing predList makes the following work:			 *	select * from t1, (select * from t2) c properties joinStrategy = hash where t1.c1 = c.c1;			 * The following works with restrictionList:			 *	select * from t1, (select c1 + 0 from t2) c(c1) properties joinStrategy = hash where t1.c1 = c.c1;			 */			optimizer.considerCost(this, restrictionList, getCostEstimate(), outerCost);		}		return costEstimate;	}	/**	 * @see Optimizable#feasibleJoinStrategy	 *	 * @exception StandardException		Thrown on error	 */	public boolean feasibleJoinStrategy(OptimizablePredicateList predList,										Optimizer optimizer)					throws StandardException	{		AccessPath ap;		/* The child being an Optimizable is a special case.  In that		 * case, we want to get the current access path and join strategy		 * from the child.  Otherwise, we want to get it from this node.		 */		if (childResult instanceof Optimizable)		{			// With DERBY-805 it's possible that, when considering a nested			// loop join with this PRN, we pushed predicates down into the			// child if the child is a UNION node.  At this point, though, we			// may be considering doing a hash join with this PRN instead of a			// nested loop join, and if that's the case we need to pull any			// predicates back up so that they can be searched for equijoins			// that will in turn make the hash join possible.  So that's what			// the next call does.  Two things to note: 1) if no predicates			// were pushed, this call is a no-op; and 2) if we get here when			// considering a nested loop join, the predicates that we pull			// here (if any) will be re-pushed for subsequent costing/ 			// optimization as necessary (see OptimizerImpl.costPermutation(),			// which will call this class's optimizeIt() method and that's			// where the predicates are pushed down again).			if (childResult instanceof UnionNode)				((UnionNode)childResult).pullOptPredicates(restrictionList);			return ((Optimizable) childResult).				feasibleJoinStrategy(restrictionList, optimizer);		}		else		{			return super.feasibleJoinStrategy(restrictionList, optimizer);		}	}	/** @see Optimizable#getCurrentAccessPath */	public AccessPath getCurrentAccessPath()	{		if (childResult instanceof Optimizable)			return ((Optimizable) childResult).getCurrentAccessPath();		return super.getCurrentAccessPath();	}	/** @see Optimizable#getBestAccessPath */	public AccessPath getBestAccessPath()	{		if (childResult instanceof Optimizable)			return ((Optimizable) childResult).getBestAccessPath();		return super.getBestAccessPath();	}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -