List of usage examples for org.apache.lucene.search SortField getComparator
public FieldComparator<?> getComparator(final int numHits, final int sortPos)
From source file:org.apache.solr.handler.component.HelloHandlerComponent.java
License:Apache License
protected void doFieldSortValues(ResponseBuilder rb, SolrIndexSearcher searcher) throws IOException { SolrQueryRequest req = rb.req;/*from www . j a v a 2s . co m*/ SolrQueryResponse rsp = rb.rsp; final CharsRef spare = new CharsRef(); // The query cache doesn't currently store sort field values, and SolrIndexSearcher doesn't // currently have an option to return sort field values. Because of this, we // take the documents given and re-derive the sort values. boolean fsv = req.getParams().getBool(ResponseBuilder.FIELD_SORT_VALUES, false); if (fsv) { Sort sort = searcher.weightSort(rb.getSortSpec().getSort()); SortField[] sortFields = sort == null ? new SortField[] { SortField.FIELD_SCORE } : sort.getSort(); NamedList<Object[]> sortVals = new NamedList<Object[]>(); // order is important for the sort fields Field field = new StringField("dummy", "", Field.Store.NO); // a dummy Field IndexReaderContext topReaderContext = searcher.getTopReaderContext(); List<AtomicReaderContext> leaves = topReaderContext.leaves(); AtomicReaderContext currentLeaf = null; if (leaves.size() == 1) { // if there is a single segment, use that subReader and avoid looking up each time currentLeaf = leaves.get(0); leaves = null; } DocList docList = rb.getResults().docList; // sort ids from lowest to highest so we can access them in order int nDocs = docList.size(); long[] sortedIds = new long[nDocs]; DocIterator it = rb.getResults().docList.iterator(); for (int i = 0; i < nDocs; i++) { sortedIds[i] = (((long) it.nextDoc()) << 32) | i; } Arrays.sort(sortedIds); for (SortField sortField : sortFields) { SortField.Type type = sortField.getType(); if (type == SortField.Type.SCORE || type == SortField.Type.DOC) continue; FieldComparator comparator = null; String fieldname = sortField.getField(); FieldType ft = fieldname == null ? null : req.getSchema().getFieldTypeNoEx(fieldname); Object[] vals = new Object[nDocs]; int lastIdx = -1; int idx = 0; for (long idAndPos : sortedIds) { int doc = (int) (idAndPos >>> 32); int position = (int) idAndPos; if (leaves != null) { idx = ReaderUtil.subIndex(doc, leaves); currentLeaf = leaves.get(idx); if (idx != lastIdx) { // we switched segments. invalidate comparator. comparator = null; } } if (comparator == null) { comparator = sortField.getComparator(1, 0); comparator = comparator.setNextReader(currentLeaf); } doc -= currentLeaf.docBase; // adjust for what segment this is in comparator.copy(0, doc); Object val = comparator.value(0); // Sortable float, double, int, long types all just use a string // comparator. For these, we need to put the type into a readable // format. One reason for this is that XML can't represent all // string values (or even all unicode code points). // indexedToReadable() should be a no-op and should // thus be harmless anyway (for all current ways anyway) if (val instanceof String) { field.setStringValue((String) val); val = ft.toObject(field); } // Must do the same conversion when sorting by a // String field in Lucene, which returns the terms // data as BytesRef: if (val instanceof BytesRef) { UnicodeUtil.UTF8toUTF16((BytesRef) val, spare); field.setStringValue(spare.toString()); val = ft.toObject(field); } vals[position] = val; } sortVals.add(fieldname, vals); } rsp.add("sort_values", sortVals); } }
From source file:org.apache.solr.handler.component.QueryComponent.java
License:Apache License
protected void doFieldSortValues(ResponseBuilder rb, SolrIndexSearcher searcher) throws IOException { SolrQueryRequest req = rb.req;/*w ww . j a va2s . c om*/ SolrQueryResponse rsp = rb.rsp; final CharsRef spare = new CharsRef(); // The query cache doesn't currently store sort field values, and SolrIndexSearcher doesn't // currently have an option to return sort field values. Because of this, we // take the documents given and re-derive the sort values. boolean fsv = req.getParams().getBool(ResponseBuilder.FIELD_SORT_VALUES, false); if (fsv) { Sort sort = searcher.weightSort(rb.getSortSpec().getSort()); SortField[] sortFields = sort == null ? new SortField[] { SortField.FIELD_SCORE } : sort.getSort(); NamedList<Object[]> sortVals = new NamedList<Object[]>(); // order is important for the sort fields Field field = new StringField("dummy", "", Field.Store.NO); // a dummy Field IndexReaderContext topReaderContext = searcher.getTopReaderContext(); List<AtomicReaderContext> leaves = topReaderContext.leaves(); AtomicReaderContext currentLeaf = null; if (leaves.size() == 1) { // if there is a single segment, use that subReader and avoid looking up each time currentLeaf = leaves.get(0); leaves = null; } DocList docList = rb.getResults().docList; // sort ids from lowest to highest so we can access them in order int nDocs = docList.size(); long[] sortedIds = new long[nDocs]; DocIterator it = rb.getResults().docList.iterator(); for (int i = 0; i < nDocs; i++) { sortedIds[i] = (((long) it.nextDoc()) << 32) | i; } Arrays.sort(sortedIds); for (SortField sortField : sortFields) { SortField.Type type = sortField.getType(); if (type == SortField.Type.SCORE || type == SortField.Type.DOC) continue; FieldComparator comparator = null; String fieldname = sortField.getField(); FieldType ft = fieldname == null ? null : searcher.getSchema().getFieldTypeNoEx(fieldname); Object[] vals = new Object[nDocs]; int lastIdx = -1; int idx = 0; for (long idAndPos : sortedIds) { int doc = (int) (idAndPos >>> 32); int position = (int) idAndPos; if (leaves != null) { idx = ReaderUtil.subIndex(doc, leaves); currentLeaf = leaves.get(idx); if (idx != lastIdx) { // we switched segments. invalidate comparator. comparator = null; } } if (comparator == null) { comparator = sortField.getComparator(1, 0); comparator = comparator.setNextReader(currentLeaf); } doc -= currentLeaf.docBase; // adjust for what segment this is in comparator.copy(0, doc); Object val = comparator.value(0); // Sortable float, double, int, long types all just use a string // comparator. For these, we need to put the type into a readable // format. One reason for this is that XML can't represent all // string values (or even all unicode code points). // indexedToReadable() should be a no-op and should // thus be harmless anyway (for all current ways anyway) if (val instanceof String) { field.setStringValue((String) val); val = ft.toObject(field); } // Must do the same conversion when sorting by a // String field in Lucene, which returns the terms // data as BytesRef: if (val instanceof BytesRef) { UnicodeUtil.UTF8toUTF16((BytesRef) val, spare); field.setStringValue(spare.toString()); val = ft.toObject(field); } vals[position] = val; } sortVals.add(fieldname, vals); } rsp.add("sort_values", sortVals); } }
From source file:org.apache.solr.handler.component.ShardFieldSortedHitQueue.java
License:Apache License
Comparator<ShardDoc> comparatorFieldComparator(SortField sortField) { final FieldComparator fieldComparator = sortField.getComparator(0, 0); return new ShardComparator(sortField) { // Since the PriorityQueue keeps the biggest elements by default, // we need to reverse the field compare ordering so that the // smallest elements are kept instead of the largest... hence // the negative sign. @Override/*w ww. ja v a2 s . c om*/ public int compare(final ShardDoc o1, final ShardDoc o2) { //noinspection unchecked return -fieldComparator.compareValues(sortVal(o1), sortVal(o2)); } }; }
From source file:org.apache.solr.search.federated.ShardFieldSortedHitQueue.java
License:Apache License
@SuppressWarnings("rawtypes") Comparator<ShardDoc> comparatorFieldComparator(SortField sortField) { final FieldComparator fieldComparator; try {// w w w . ja v a 2 s .c om fieldComparator = sortField.getComparator(0, 0); } catch (IOException e) { throw new RuntimeException("Unable to get FieldComparator for sortField " + sortField); } return new ShardComparator(sortField) { // Since the PriorityQueue keeps the biggest elements by default, // we need to reverse the field compare ordering so that the // smallest elements are kept instead of the largest... hence // the negative sign. @Override @SuppressWarnings("unchecked") public int compare(final ShardDoc o1, final ShardDoc o2) { // noinspection unchecked return -fieldComparator.compareValues(sortVal(o1), sortVal(o2)); } }; }
From source file:org.apache.solr.search.MultiCollector.java
License:Apache License
public TopGroupCollector(ValueSource groupByVS, Map vsContext, Sort sort, int nGroups) throws IOException { this.vs = groupByVS; this.context = vsContext; this.nGroups = nGroups; SortField[] sortFields = sort.getSort(); this.comparators = new FieldComparator[sortFields.length]; this.reversed = new int[sortFields.length]; for (int i = 0; i < sortFields.length; i++) { SortField sortField = sortFields[i]; reversed[i] = sortField.getReverse() ? -1 : 1; // use nGroups + 1 so we have a spare slot to use for comparing (tracked by this.spareSlot) comparators[i] = sortField.getComparator(nGroups + 1, i); }/* w ww . ja v a 2s . c o m*/ this.spareSlot = nGroups; this.groupMap = new HashMap<MutableValue, SearchGroup>(nGroups); }
From source file:org.apache.solr.search.MultiCollector.java
License:Apache License
void constructComparators(FieldComparator[] comparators, int[] reversed, SortField[] sortFields, int size) throws IOException { for (int i = 0; i < sortFields.length; i++) { SortField sortField = sortFields[i]; reversed[i] = sortField.getReverse() ? -1 : 1; comparators[i] = sortField.getComparator(size, i); if (scorer != null) comparators[i].setScorer(scorer); if (reader != null) comparators[i].setNextReader(reader, docBase); }// w ww.jav a 2 s.c o m }