Loading src/main/java/messif/algorithms/impl/FileSequentialScan.java +5 −3 Original line number Diff line number Diff line Loading @@ -27,6 +27,7 @@ import java.util.concurrent.Executors; import java.util.concurrent.Future; import java.util.logging.Level; import java.util.logging.Logger; import messif.algorithms.Algorithm; import messif.objects.LocalAbstractObject; import messif.objects.util.AbstractObjectIterator; Loading @@ -35,6 +36,7 @@ import messif.operations.QueryOperation; import messif.operations.query.GetAlgorithmInfoOperation; import messif.operations.RankingSingleQueryOperation; import messif.operations.query.BatchKNNQueryOperation; import messif.operations.query.BatchRankingQueryOperation; import messif.utility.Convert; /** Loading Loading @@ -107,13 +109,13 @@ public class FileSequentialScan extends Algorithm { } /** * Processes the batch k-NN operation; the batch is split into sub-batches which are processed * Processes the batch ranking operation; the batch is split into sub-batches which are processed * in parallel. A separate thread reads the data from the data file. * @param operation batch operation to be processed * @throws IOException if the data file cannot be read * @throws ClassNotFoundException if the specified data class is not valid */ public void batchQuerySearch(BatchKNNQueryOperation operation) throws IOException, ClassNotFoundException { public void batchQuerySearch(BatchRankingQueryOperation operation) throws IOException, ClassNotFoundException { List<Future> futures = new ArrayList<>(); // list of all data queues used by individual query batches Loading @@ -130,7 +132,7 @@ public class FileSequentialScan extends Algorithm { operationBatch.add(operation.getOperation(queryCounter)); } while ((++ queryCounter % queryBatchSize) != 0 && queryCounter < operation.getNOperations()); // start thread that will process a sub-batch of KNN operations // start thread that will process a sub-batch of ranking operations futures.add(getOperationsThreadPool().submit(new EvaluationThread(operationBatch, dataBatch))); } Loading src/main/java/messif/operations/query/BatchKNNQueryOperation.java +14 −127 Original line number Diff line number Diff line Loading @@ -17,15 +17,12 @@ package messif.operations.query; import java.util.ArrayList; import java.util.Collections; import java.util.Iterator; import java.util.List; import messif.objects.util.AbstractObjectIterator; import messif.objects.util.StreamGenericAbstractObjectIterator; import messif.objects.LocalAbstractObject; import messif.operations.AbstractOperation; import messif.operations.AnswerType; import messif.operations.OperationErrorCode; import messif.operations.QueryOperation; /** * A batch of several K-nearest neighbors query operations encapsulated as a single operation. Loading @@ -33,16 +30,13 @@ import messif.operations.QueryOperation; * @author Michal Batko, Masaryk University, Brno, Czech Republic, batko@fi.muni.cz * @author Vlastislav Dohnal, Masaryk University, Brno, Czech Republic, dohnal@fi.muni.cz * @author David Novak, Masaryk University, Brno, Czech Republic, david.novak@fi.muni.cz * @author Honza Brázdil, janinko.g@gmail.com */ @AbstractOperation.OperationName("k-nearest neighbors query") public class BatchKNNQueryOperation extends QueryOperation { public class BatchKNNQueryOperation extends BatchRankingQueryOperation<KNNQueryOperation> { /** Class serial id for serialization */ private static final long serialVersionUID = 1L; //****************** Attributes ******************// private final List<KNNQueryOperation> knnOperations ; private static final long serialVersionUID = 2L; //****************** Constructors ******************// Loading @@ -52,7 +46,7 @@ public class BatchKNNQueryOperation extends QueryOperation { * @param k the number of nearest neighbors to retrieve for each operation */ @AbstractOperation.OperationConstructor({"Query object", "Number of nearest objects"}) public BatchKNNQueryOperation(StreamGenericAbstractObjectIterator queryObjects, int k) { public BatchKNNQueryOperation(Iterator<? extends LocalAbstractObject> queryObjects, int k) { this(queryObjects, k, AnswerType.NODATA_OBJECTS); } Loading @@ -63,136 +57,29 @@ public class BatchKNNQueryOperation extends QueryOperation { * @param answerType the type of objects this operation stores in its answer */ @AbstractOperation.OperationConstructor({"Query object", "Number of nearest objects", "Answer type"}) public BatchKNNQueryOperation(StreamGenericAbstractObjectIterator queryObjects, int k, AnswerType answerType) { public BatchKNNQueryOperation(Iterator<? extends LocalAbstractObject> queryObjects, int k, AnswerType answerType) { this(queryObjects, Integer.MAX_VALUE, k, answerType); } /** * Creates a list of {@link KNNQueryOperation} for all specified query objects. * Creates a list of {@link KNNQueryOperation} for part of specified query objects. * @param queryObjects iterator over the query objects * @param maxNQueries maximal number of query objects read from the iterator (can be {@code Integer.MAX_VALUE} * @param k the number of nearest neighbors to retrieve for each operation * @param answerType the type of objects this operation stores in its answer */ @AbstractOperation.OperationConstructor({"Query object", "Number of nearest objects", "Store the meta-object subdistances?", "Answer type"}) public BatchKNNQueryOperation(StreamGenericAbstractObjectIterator queryObjects, int maxNQueries, int k, AnswerType answerType) { super(answerType); public BatchKNNQueryOperation(Iterator<? extends LocalAbstractObject> queryObjects, int maxNQueries, int k, AnswerType answerType) { super(constructKNNQueryies(queryObjects, maxNQueries, k, answerType), answerType); } private static List<KNNQueryOperation> constructKNNQueryies(Iterator<? extends LocalAbstractObject> queryObjects, int maxNQueries, int k, AnswerType answerType){ List<KNNQueryOperation> operations = new ArrayList<>(); int i = 0; while (queryObjects.hasNext() && i ++ < maxNQueries) { operations.add(new KNNQueryOperation(queryObjects.next(), k, answerType)); } this.knnOperations = Collections.unmodifiableList(operations); } //****************** Attribute access ******************// public int getNOperations() { return knnOperations.size(); } public KNNQueryOperation getOperation(int index) { return knnOperations.get(index); } public List<KNNQueryOperation> getKnnOperations() { return knnOperations; } /** * Returns argument that was passed while constructing instance. * If the argument is not stored within operation, <tt>null</tt> is returned. * @param index index of an argument passed to constructor * @return argument that was passed while constructing instance * @throws IndexOutOfBoundsException if index parameter is out of range */ @Override public Object getArgument(int index) throws IndexOutOfBoundsException { switch (index) { default: throw new IndexOutOfBoundsException("kNNQueryOperation has only two arguments"); } return operations; } /** * Returns number of arguments that were passed while constructing this instance. * @return number of arguments that were passed while constructing this instance */ @Override public int getArgumentCount() { return 0; } @Override public boolean wasSuccessful() { return getErrorCode() == OperationErrorCode.RESPONSE_RETURNED; } @Override public void endOperation() { endOperation(OperationErrorCode.RESPONSE_RETURNED); } @Override public int evaluate(AbstractObjectIterator objects) { throw new UnsupportedOperationException("Not supported yet."); //To change body of generated methods, choose Tools | Templates. } @Override public Class getAnswerClass() { if (knnOperations.isEmpty()) { return null; } return (knnOperations.get(0).getAnswerClass()); } @Override public int getAnswerCount() { return 0; } @Override public Iterator getAnswer() { return Collections.emptyIterator(); } @Override public Iterator getAnswer(int skip, int count) { return Collections.emptyIterator(); } @Override public Iterator getAnswerObjects() { return Collections.emptyIterator(); } @Override public void resetAnswer() { } @Override public int getSubAnswerCount() { return knnOperations.size(); } @Override public Iterator getSubAnswer(int index) throws IndexOutOfBoundsException { return knnOperations.get(index).getAnswer(); } @Override public Iterator getSubAnswer(Object key) { throw new UnsupportedOperationException("Not supported yet."); //To change body of generated methods, choose Tools | Templates. } @Override protected boolean dataEqualsImpl(QueryOperation operation) { throw new UnsupportedOperationException("Not supported yet."); //To change body of generated methods, choose Tools | Templates. } @Override public int dataHashCode() { throw new UnsupportedOperationException("Not supported yet."); //To change body of generated methods, choose Tools | Templates. } } src/main/java/messif/operations/query/BatchRankingQueryOperation.java 0 → 100644 +186 −0 Original line number Diff line number Diff line /* * This file is part of MESSIF library. * * MESSIF library is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * MESSIF 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 General Public License for more details. * * You should have received a copy of the GNU General Public License * along with MESSIF library. If not, see <http://www.gnu.org/licenses/>. */ package messif.operations.query; import java.util.ArrayList; import java.util.Collection; import java.util.Collections; import java.util.Iterator; import java.util.List; import messif.objects.util.AbstractObjectIterator; import messif.operations.AbstractOperation; import messif.operations.AnswerType; import messif.operations.OperationErrorCode; import messif.operations.QueryOperation; import messif.operations.RankingSingleQueryOperation; /** * A batch of several ranking query operations encapsulated as a single operation. * * @author Michal Batko, Masaryk University, Brno, Czech Republic, batko@fi.muni.cz * @author Vlastislav Dohnal, Masaryk University, Brno, Czech Republic, dohnal@fi.muni.cz * @author David Novak, Masaryk University, Brno, Czech Republic, david.novak@fi.muni.cz * @author Honza Brázdil, janinko.g@gmail.com * @param <T> Type of the ranking query operation. */ @AbstractOperation.OperationName("k-nearest neighbors query") public class BatchRankingQueryOperation<T extends RankingSingleQueryOperation> extends QueryOperation { /** Class serial id for serialization */ private static final long serialVersionUID = 1L; //****************** Attributes ******************// private final List<T> operations ; //****************** Constructors ******************// /** * Creates a list of {@link RankingSingleQueryOperation} for all specified query operation. * @param operations Collection of ranking operations. */ @AbstractOperation.OperationConstructor({"Query object", "Number of nearest objects"}) public BatchRankingQueryOperation(Collection<T> operations) { this(operations, AnswerType.NODATA_OBJECTS); } /** * Creates a list of {@link RankingSingleQueryOperation} for all specified query operation. * @param operations Collection of ranking operations. * @param answerType the type of objects this operation stores in its answer */ @AbstractOperation.OperationConstructor({"Query object", "Number of nearest objects", "Answer type"}) public BatchRankingQueryOperation(Collection<T> operations, AnswerType answerType) { super(answerType); this.operations = Collections.unmodifiableList(new ArrayList<>(operations)); for(T operation : operations){ operation.setAnswerType(answerType); } } //****************** Attribute access ******************// public int getNOperations() { return operations.size(); } public T getOperation(int index) { return operations.get(index); } public List<T> getKnnOperations() { return operations; } /** * Returns argument that was passed while constructing instance. * If the argument is not stored within operation, <tt>null</tt> is returned. * @param index index of an argument passed to constructor * @return argument that was passed while constructing instance * @throws IndexOutOfBoundsException if index parameter is out of range */ @Override public Object getArgument(int index) throws IndexOutOfBoundsException { switch (index) { default: throw new IndexOutOfBoundsException("kNNQueryOperation has only two arguments"); } } /** * Returns number of arguments that were passed while constructing this instance. * @return number of arguments that were passed while constructing this instance */ @Override public int getArgumentCount() { return 0; } @Override public boolean wasSuccessful() { return getErrorCode() == OperationErrorCode.RESPONSE_RETURNED; } @Override public void endOperation() { endOperation(OperationErrorCode.RESPONSE_RETURNED); } @Override public int evaluate(AbstractObjectIterator objects) { throw new UnsupportedOperationException("Not supported yet."); //To change body of generated methods, choose Tools | Templates. } @Override public Class getAnswerClass() { if (operations.isEmpty()) { return null; } return (operations.get(0).getAnswerClass()); } @Override public int getAnswerCount() { return 0; } @Override public Iterator getAnswer() { return Collections.emptyIterator(); } @Override public Iterator getAnswer(int skip, int count) { return Collections.emptyIterator(); } @Override public Iterator getAnswerObjects() { return Collections.emptyIterator(); } @Override public void resetAnswer() { } @Override public int getSubAnswerCount() { return operations.size(); } @Override public Iterator getSubAnswer(int index) throws IndexOutOfBoundsException { return operations.get(index).getAnswer(); } @Override public Iterator getSubAnswer(Object key) { throw new UnsupportedOperationException("Not supported yet."); //To change body of generated methods, choose Tools | Templates. } @Override protected boolean dataEqualsImpl(QueryOperation operation) { throw new UnsupportedOperationException("Not supported yet."); //To change body of generated methods, choose Tools | Templates. } @Override public int dataHashCode() { throw new UnsupportedOperationException("Not supported yet."); //To change body of generated methods, choose Tools | Templates. } } Loading
src/main/java/messif/algorithms/impl/FileSequentialScan.java +5 −3 Original line number Diff line number Diff line Loading @@ -27,6 +27,7 @@ import java.util.concurrent.Executors; import java.util.concurrent.Future; import java.util.logging.Level; import java.util.logging.Logger; import messif.algorithms.Algorithm; import messif.objects.LocalAbstractObject; import messif.objects.util.AbstractObjectIterator; Loading @@ -35,6 +36,7 @@ import messif.operations.QueryOperation; import messif.operations.query.GetAlgorithmInfoOperation; import messif.operations.RankingSingleQueryOperation; import messif.operations.query.BatchKNNQueryOperation; import messif.operations.query.BatchRankingQueryOperation; import messif.utility.Convert; /** Loading Loading @@ -107,13 +109,13 @@ public class FileSequentialScan extends Algorithm { } /** * Processes the batch k-NN operation; the batch is split into sub-batches which are processed * Processes the batch ranking operation; the batch is split into sub-batches which are processed * in parallel. A separate thread reads the data from the data file. * @param operation batch operation to be processed * @throws IOException if the data file cannot be read * @throws ClassNotFoundException if the specified data class is not valid */ public void batchQuerySearch(BatchKNNQueryOperation operation) throws IOException, ClassNotFoundException { public void batchQuerySearch(BatchRankingQueryOperation operation) throws IOException, ClassNotFoundException { List<Future> futures = new ArrayList<>(); // list of all data queues used by individual query batches Loading @@ -130,7 +132,7 @@ public class FileSequentialScan extends Algorithm { operationBatch.add(operation.getOperation(queryCounter)); } while ((++ queryCounter % queryBatchSize) != 0 && queryCounter < operation.getNOperations()); // start thread that will process a sub-batch of KNN operations // start thread that will process a sub-batch of ranking operations futures.add(getOperationsThreadPool().submit(new EvaluationThread(operationBatch, dataBatch))); } Loading
src/main/java/messif/operations/query/BatchKNNQueryOperation.java +14 −127 Original line number Diff line number Diff line Loading @@ -17,15 +17,12 @@ package messif.operations.query; import java.util.ArrayList; import java.util.Collections; import java.util.Iterator; import java.util.List; import messif.objects.util.AbstractObjectIterator; import messif.objects.util.StreamGenericAbstractObjectIterator; import messif.objects.LocalAbstractObject; import messif.operations.AbstractOperation; import messif.operations.AnswerType; import messif.operations.OperationErrorCode; import messif.operations.QueryOperation; /** * A batch of several K-nearest neighbors query operations encapsulated as a single operation. Loading @@ -33,16 +30,13 @@ import messif.operations.QueryOperation; * @author Michal Batko, Masaryk University, Brno, Czech Republic, batko@fi.muni.cz * @author Vlastislav Dohnal, Masaryk University, Brno, Czech Republic, dohnal@fi.muni.cz * @author David Novak, Masaryk University, Brno, Czech Republic, david.novak@fi.muni.cz * @author Honza Brázdil, janinko.g@gmail.com */ @AbstractOperation.OperationName("k-nearest neighbors query") public class BatchKNNQueryOperation extends QueryOperation { public class BatchKNNQueryOperation extends BatchRankingQueryOperation<KNNQueryOperation> { /** Class serial id for serialization */ private static final long serialVersionUID = 1L; //****************** Attributes ******************// private final List<KNNQueryOperation> knnOperations ; private static final long serialVersionUID = 2L; //****************** Constructors ******************// Loading @@ -52,7 +46,7 @@ public class BatchKNNQueryOperation extends QueryOperation { * @param k the number of nearest neighbors to retrieve for each operation */ @AbstractOperation.OperationConstructor({"Query object", "Number of nearest objects"}) public BatchKNNQueryOperation(StreamGenericAbstractObjectIterator queryObjects, int k) { public BatchKNNQueryOperation(Iterator<? extends LocalAbstractObject> queryObjects, int k) { this(queryObjects, k, AnswerType.NODATA_OBJECTS); } Loading @@ -63,136 +57,29 @@ public class BatchKNNQueryOperation extends QueryOperation { * @param answerType the type of objects this operation stores in its answer */ @AbstractOperation.OperationConstructor({"Query object", "Number of nearest objects", "Answer type"}) public BatchKNNQueryOperation(StreamGenericAbstractObjectIterator queryObjects, int k, AnswerType answerType) { public BatchKNNQueryOperation(Iterator<? extends LocalAbstractObject> queryObjects, int k, AnswerType answerType) { this(queryObjects, Integer.MAX_VALUE, k, answerType); } /** * Creates a list of {@link KNNQueryOperation} for all specified query objects. * Creates a list of {@link KNNQueryOperation} for part of specified query objects. * @param queryObjects iterator over the query objects * @param maxNQueries maximal number of query objects read from the iterator (can be {@code Integer.MAX_VALUE} * @param k the number of nearest neighbors to retrieve for each operation * @param answerType the type of objects this operation stores in its answer */ @AbstractOperation.OperationConstructor({"Query object", "Number of nearest objects", "Store the meta-object subdistances?", "Answer type"}) public BatchKNNQueryOperation(StreamGenericAbstractObjectIterator queryObjects, int maxNQueries, int k, AnswerType answerType) { super(answerType); public BatchKNNQueryOperation(Iterator<? extends LocalAbstractObject> queryObjects, int maxNQueries, int k, AnswerType answerType) { super(constructKNNQueryies(queryObjects, maxNQueries, k, answerType), answerType); } private static List<KNNQueryOperation> constructKNNQueryies(Iterator<? extends LocalAbstractObject> queryObjects, int maxNQueries, int k, AnswerType answerType){ List<KNNQueryOperation> operations = new ArrayList<>(); int i = 0; while (queryObjects.hasNext() && i ++ < maxNQueries) { operations.add(new KNNQueryOperation(queryObjects.next(), k, answerType)); } this.knnOperations = Collections.unmodifiableList(operations); } //****************** Attribute access ******************// public int getNOperations() { return knnOperations.size(); } public KNNQueryOperation getOperation(int index) { return knnOperations.get(index); } public List<KNNQueryOperation> getKnnOperations() { return knnOperations; } /** * Returns argument that was passed while constructing instance. * If the argument is not stored within operation, <tt>null</tt> is returned. * @param index index of an argument passed to constructor * @return argument that was passed while constructing instance * @throws IndexOutOfBoundsException if index parameter is out of range */ @Override public Object getArgument(int index) throws IndexOutOfBoundsException { switch (index) { default: throw new IndexOutOfBoundsException("kNNQueryOperation has only two arguments"); } return operations; } /** * Returns number of arguments that were passed while constructing this instance. * @return number of arguments that were passed while constructing this instance */ @Override public int getArgumentCount() { return 0; } @Override public boolean wasSuccessful() { return getErrorCode() == OperationErrorCode.RESPONSE_RETURNED; } @Override public void endOperation() { endOperation(OperationErrorCode.RESPONSE_RETURNED); } @Override public int evaluate(AbstractObjectIterator objects) { throw new UnsupportedOperationException("Not supported yet."); //To change body of generated methods, choose Tools | Templates. } @Override public Class getAnswerClass() { if (knnOperations.isEmpty()) { return null; } return (knnOperations.get(0).getAnswerClass()); } @Override public int getAnswerCount() { return 0; } @Override public Iterator getAnswer() { return Collections.emptyIterator(); } @Override public Iterator getAnswer(int skip, int count) { return Collections.emptyIterator(); } @Override public Iterator getAnswerObjects() { return Collections.emptyIterator(); } @Override public void resetAnswer() { } @Override public int getSubAnswerCount() { return knnOperations.size(); } @Override public Iterator getSubAnswer(int index) throws IndexOutOfBoundsException { return knnOperations.get(index).getAnswer(); } @Override public Iterator getSubAnswer(Object key) { throw new UnsupportedOperationException("Not supported yet."); //To change body of generated methods, choose Tools | Templates. } @Override protected boolean dataEqualsImpl(QueryOperation operation) { throw new UnsupportedOperationException("Not supported yet."); //To change body of generated methods, choose Tools | Templates. } @Override public int dataHashCode() { throw new UnsupportedOperationException("Not supported yet."); //To change body of generated methods, choose Tools | Templates. } }
src/main/java/messif/operations/query/BatchRankingQueryOperation.java 0 → 100644 +186 −0 Original line number Diff line number Diff line /* * This file is part of MESSIF library. * * MESSIF library is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * MESSIF 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 General Public License for more details. * * You should have received a copy of the GNU General Public License * along with MESSIF library. If not, see <http://www.gnu.org/licenses/>. */ package messif.operations.query; import java.util.ArrayList; import java.util.Collection; import java.util.Collections; import java.util.Iterator; import java.util.List; import messif.objects.util.AbstractObjectIterator; import messif.operations.AbstractOperation; import messif.operations.AnswerType; import messif.operations.OperationErrorCode; import messif.operations.QueryOperation; import messif.operations.RankingSingleQueryOperation; /** * A batch of several ranking query operations encapsulated as a single operation. * * @author Michal Batko, Masaryk University, Brno, Czech Republic, batko@fi.muni.cz * @author Vlastislav Dohnal, Masaryk University, Brno, Czech Republic, dohnal@fi.muni.cz * @author David Novak, Masaryk University, Brno, Czech Republic, david.novak@fi.muni.cz * @author Honza Brázdil, janinko.g@gmail.com * @param <T> Type of the ranking query operation. */ @AbstractOperation.OperationName("k-nearest neighbors query") public class BatchRankingQueryOperation<T extends RankingSingleQueryOperation> extends QueryOperation { /** Class serial id for serialization */ private static final long serialVersionUID = 1L; //****************** Attributes ******************// private final List<T> operations ; //****************** Constructors ******************// /** * Creates a list of {@link RankingSingleQueryOperation} for all specified query operation. * @param operations Collection of ranking operations. */ @AbstractOperation.OperationConstructor({"Query object", "Number of nearest objects"}) public BatchRankingQueryOperation(Collection<T> operations) { this(operations, AnswerType.NODATA_OBJECTS); } /** * Creates a list of {@link RankingSingleQueryOperation} for all specified query operation. * @param operations Collection of ranking operations. * @param answerType the type of objects this operation stores in its answer */ @AbstractOperation.OperationConstructor({"Query object", "Number of nearest objects", "Answer type"}) public BatchRankingQueryOperation(Collection<T> operations, AnswerType answerType) { super(answerType); this.operations = Collections.unmodifiableList(new ArrayList<>(operations)); for(T operation : operations){ operation.setAnswerType(answerType); } } //****************** Attribute access ******************// public int getNOperations() { return operations.size(); } public T getOperation(int index) { return operations.get(index); } public List<T> getKnnOperations() { return operations; } /** * Returns argument that was passed while constructing instance. * If the argument is not stored within operation, <tt>null</tt> is returned. * @param index index of an argument passed to constructor * @return argument that was passed while constructing instance * @throws IndexOutOfBoundsException if index parameter is out of range */ @Override public Object getArgument(int index) throws IndexOutOfBoundsException { switch (index) { default: throw new IndexOutOfBoundsException("kNNQueryOperation has only two arguments"); } } /** * Returns number of arguments that were passed while constructing this instance. * @return number of arguments that were passed while constructing this instance */ @Override public int getArgumentCount() { return 0; } @Override public boolean wasSuccessful() { return getErrorCode() == OperationErrorCode.RESPONSE_RETURNED; } @Override public void endOperation() { endOperation(OperationErrorCode.RESPONSE_RETURNED); } @Override public int evaluate(AbstractObjectIterator objects) { throw new UnsupportedOperationException("Not supported yet."); //To change body of generated methods, choose Tools | Templates. } @Override public Class getAnswerClass() { if (operations.isEmpty()) { return null; } return (operations.get(0).getAnswerClass()); } @Override public int getAnswerCount() { return 0; } @Override public Iterator getAnswer() { return Collections.emptyIterator(); } @Override public Iterator getAnswer(int skip, int count) { return Collections.emptyIterator(); } @Override public Iterator getAnswerObjects() { return Collections.emptyIterator(); } @Override public void resetAnswer() { } @Override public int getSubAnswerCount() { return operations.size(); } @Override public Iterator getSubAnswer(int index) throws IndexOutOfBoundsException { return operations.get(index).getAnswer(); } @Override public Iterator getSubAnswer(Object key) { throw new UnsupportedOperationException("Not supported yet."); //To change body of generated methods, choose Tools | Templates. } @Override protected boolean dataEqualsImpl(QueryOperation operation) { throw new UnsupportedOperationException("Not supported yet."); //To change body of generated methods, choose Tools | Templates. } @Override public int dataHashCode() { throw new UnsupportedOperationException("Not supported yet."); //To change body of generated methods, choose Tools | Templates. } }