/* XXL: The eXtensible and fleXible Library for data processing
Copyright (C) 2000-2011 Prof. Dr. Bernhard Seeger
Head of the Database Research Group
Department of Mathematics and Computer Science
University of Marburg
Germany
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Lesser General Public
License as published by the Free Software Foundation; either
version 3 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Lesser General Public License for more details.
You should have received a copy of the GNU Lesser General Public
License along with this library; If not, see <http://www.gnu.org/licenses/>.
http://code.google.com/p/xxl/
*/
package xxl.core.relational.cursors;
import java.sql.ResultSet;
import java.sql.ResultSetMetaData;
import xxl.core.cursors.MetaDataCursor;
import xxl.core.functions.AbstractFunction;
import xxl.core.functions.Function;
import xxl.core.predicates.Predicate;
import xxl.core.relational.JoinUtils;
import xxl.core.relational.metaData.ResultSetMetaDatas;
import xxl.core.relational.tuples.Tuple;
import xxl.core.util.metaData.CompositeMetaData;
import xxl.core.util.metaData.MetaDataException;
/**
* Operator that computes an intersection using the nested-loops paradigm.
*/
public class NestedLoopsIntersection extends xxl.core.cursors.intersections.NestedLoopsIntersection<Tuple> implements MetaDataCursor<Tuple, CompositeMetaData<Object, Object>> {
/**
* An internal variable used for storing the metadata information of this
* intersect operator.
*/
protected CompositeMetaData<Object, Object> globalMetaData;
/**
* Constructs a new nested-loops intersection.
*
* @param input0 the input metadata cursor that is traversed in the "outer"
* loop.
* @param input1 the input metadata cursor that is traversed in the "inner"
* loop.
* @param newCursor a function without parameters that delivers a new
* metadata cursor, when the cursor <code>input1</code> cannot be
* reset, i.e., <code>input1.reset()</code> will cause an
* {@link java.lang.UnsupportedOperationException}.
* @param equals the binary predicate evaluated for each tuple of elements
* backed on one element of each input iteration in order to select
* them. Only these tuples where the predicate's evaluation result
* is <code>true</code> have been qualified to be a result of the
* intersection operation.
*/
public NestedLoopsIntersection(MetaDataCursor<? extends Tuple, CompositeMetaData<Object, Object>> input0, MetaDataCursor<? extends Tuple, CompositeMetaData<Object, Object>> input1, Function<?, ? extends MetaDataCursor<? extends Tuple, CompositeMetaData<Object, Object>>> newCursor, Predicate<? super Tuple> equals) {
super(input0, input1, newCursor, equals);
ResultSetMetaData metaData0 = ResultSetMetaDatas.getResultSetMetaData(input0);
ResultSetMetaData metaData1 = ResultSetMetaDatas.getResultSetMetaData(input1);
if (ResultSetMetaDatas.RESULTSET_METADATA_COMPARATOR.compare(metaData0, metaData1) != 0)
throw new MetaDataException("the difference of the given cursors cannot be computed because they differ in their relational metadata");
globalMetaData = new CompositeMetaData<Object, Object>();
globalMetaData.add(ResultSetMetaDatas.RESULTSET_METADATA_TYPE, metaData0);
}
/**
* Constructs a new nested-loops intersection.
*
* @param input0 the input metadata cursor that is traversed in the "outer"
* loop.
* @param input1 the input metadata cursor that is traversed in the "inner"
* loop.
* @param newCursor a function without parameters that delivers a new
* metadata cursor, when the cursor <code>input1</code> cannot be
* reset, i.e., <code>input1.reset()</code> will cause an
* {@link java.lang.UnsupportedOperationException}.
*/
public NestedLoopsIntersection(MetaDataCursor<? extends Tuple, CompositeMetaData<Object, Object>> input0, MetaDataCursor<? extends Tuple, CompositeMetaData<Object, Object>> input1, Function<?, ? extends MetaDataCursor<? extends Tuple, CompositeMetaData<Object, Object>>> newCursor) {
this(input0, input1, newCursor, JoinUtils.naturalJoinMetaDataPredicate(ResultSetMetaDatas.getResultSetMetaData(input0), ResultSetMetaDatas.getResultSetMetaData(input1)));
}
/**
* Constructs a new nested-loops intersection.
*
* @param resultSet0 the input result set that is traversed in the "outer"
* loop.
* @param resultSet1 the input result set that is traversed in the "inner"
* loop.
* @param newResultSet a function without parameters that delivers a new
* result set, when the iterating over the "inner" result set
* <code>resultSet1</code> cannot be reset, i.e.,
* <code>input1.reset()</code> will cause an
* {@link java.lang.UnsupportedOperationException}.
*/
public NestedLoopsIntersection(ResultSet resultSet0, ResultSet resultSet1, final Function<?, ? extends ResultSet> newResultSet) {
this(
new ResultSetMetaDataCursor(resultSet0),
new ResultSetMetaDataCursor(resultSet1),
new AbstractFunction<Object, MetaDataCursor<Tuple, CompositeMetaData<Object, Object>>>() {
@Override
public MetaDataCursor<Tuple, CompositeMetaData<Object, Object>> invoke() {
return new ResultSetMetaDataCursor(newResultSet.invoke());
}
}
);
}
/**
* Returns the metadata information for this metadata-cursor as a composite
* metadata ({@link CompositeMetaData}).
*
* @return the metadata information for this metadata-cursor as a composite
* metadata ({@link CompositeMetaData}).
*/
public CompositeMetaData<Object, Object> getMetaData() {
return globalMetaData;
}
}