Clover Coverage Report
Coverage timestamp: Fri May 9 2008 10:54:27 EST
../../../../img/srcFileCovDistChart10.png 0% of files have more coverage
70   167   29   14
34   87   0.41   5
5     5.8  
1    
 
  FieldDocSortedHitQueue       Line # 34 70 29 96.3% 0.96330273
 
  (11)
 
1    package org.apache.lucene.search;
2   
3    /**
4    * Copyright 2004 The Apache Software Foundation
5    *
6    * Licensed under the Apache License, Version 2.0 (the "License");
7    * you may not use this file except in compliance with the License.
8    * You may obtain a copy of the License at
9    *
10    * http://www.apache.org/licenses/LICENSE-2.0
11    *
12    * Unless required by applicable law or agreed to in writing, software
13    * distributed under the License is distributed on an "AS IS" BASIS,
14    * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15    * See the License for the specific language governing permissions and
16    * limitations under the License.
17    */
18   
19    import org.apache.lucene.util.PriorityQueue;
20   
21    import java.text.Collator;
22    import java.util.Locale;
23   
24    /**
25    * Expert: Collects sorted results from Searchable's and collates them.
26    * The elements put into this queue must be of type FieldDoc.
27    *
28    * <p>Created: Feb 11, 2004 2:04:21 PM
29    *
30    * @author Tim Jones (Nacimiento Software)
31    * @since lucene 1.4
32    * @version $Id: FieldDocSortedHitQueue.java 413201 2006-06-10 01:23:22Z gsingers $
33    */
 
34    class FieldDocSortedHitQueue
35    extends PriorityQueue {
36   
37    // this cannot contain AUTO fields - any AUTO fields should
38    // have been resolved by the time this class is used.
39    volatile SortField[] fields;
40   
41    // used in the case where the fields are sorted by locale
42    // based strings
43    volatile Collator[] collators;
44   
45   
46    /**
47    * Creates a hit queue sorted by the given list of fields.
48    * @param fields Fieldable names, in priority order (highest priority first).
49    * @param size The number of hits to retain. Must be greater than zero.
50    */
 
51  125 toggle FieldDocSortedHitQueue (SortField[] fields, int size) {
52  125 this.fields = fields;
53  125 this.collators = hasCollators (fields);
54  125 initialize (size);
55    }
56   
57   
58    /**
59    * Allows redefinition of sort fields if they are <code>null</code>.
60    * This is to handle the case using ParallelMultiSearcher where the
61    * original list contains AUTO and we don't know the actual sort
62    * type until the values come back. The fields can only be set once.
63    * This method is thread safe.
64    * @param fields
65    */
 
66  42 toggle synchronized void setFields (SortField[] fields) {
67  42 if (this.fields == null) {
68  22 this.fields = fields;
69  22 this.collators = hasCollators (fields);
70    }
71    }
72   
73   
74    /** Returns the fields being used to sort. */
 
75  125 toggle SortField[] getFields() {
76  125 return fields;
77    }
78   
79   
80    /** Returns an array of collators, possibly <code>null</code>. The collators
81    * correspond to any SortFields which were given a specific locale.
82    * @param fields Array of sort fields.
83    * @return Array, possibly <code>null</code>.
84    */
 
85  147 toggle private Collator[] hasCollators (final SortField[] fields) {
86  147 if (fields == null) return null;
87  125 Collator[] ret = new Collator[fields.length];
88  354 for (int i=0; i<fields.length; ++i) {
89  229 Locale locale = fields[i].getLocale();
90  229 if (locale != null)
91  9 ret[i] = Collator.getInstance (locale);
92    }
93  125 return ret;
94    }
95   
96   
97    /**
98    * Returns whether <code>a</code> is less relevant than <code>b</code>.
99    * @param a ScoreDoc
100    * @param b ScoreDoc
101    * @return <code>true</code> if document <code>a</code> should be sorted after document <code>b</code>.
102    */
 
103  36444 toggle protected final boolean lessThan (final Object a, final Object b) {
104  36444 final FieldDoc docA = (FieldDoc) a;
105  36444 final FieldDoc docB = (FieldDoc) b;
106  36444 final int n = fields.length;
107  36444 int c = 0;
108  85657 for (int i=0; i<n && c==0; ++i) {
109  49213 final int type = fields[i].getType();
110  49213 switch (type) {
111  12703 case SortField.SCORE:
112  12703 float r1 = ((Float)docA.fields[i]).floatValue();
113  12703 float r2 = ((Float)docB.fields[i]).floatValue();
114  12703 if (r1 > r2) c = -1;
115  12703 if (r1 < r2) c = 1;
116  12703 break;
117  400 case SortField.DOC:
118  34526 case SortField.INT:
119  34926 int i1 = ((Integer)docA.fields[i]).intValue();
120  34926 int i2 = ((Integer)docB.fields[i]).intValue();
121  34926 if (i1 < i2) c = -1;
122  34926 if (i1 > i2) c = 1;
123  34926 break;
124  720 case SortField.STRING:
125  720 String s1 = (String) docA.fields[i];
126  720 String s2 = (String) docB.fields[i];
127    // null values need to be sorted first, because of how FieldCache.getStringIndex()
128    // works - in that routine, any documents without a value in the given field are
129    // put first. If both are null, the next SortField is used
130  20 if (s1 == null) c = (s2==null) ? 0 : -1;
131  700 else if (s2 == null) c = 1; //
132  699 else if (fields[i].getLocale() == null) {
133  409 c = s1.compareTo(s2);
134    } else {
135  290 c = collators[i].compare (s1, s2);
136    }
137  720 break;
138  816 case SortField.FLOAT:
139  816 float f1 = ((Float)docA.fields[i]).floatValue();
140  816 float f2 = ((Float)docB.fields[i]).floatValue();
141  816 if (f1 < f2) c = -1;
142  816 if (f1 > f2) c = 1;
143  816 break;
144  48 case SortField.CUSTOM:
145  48 c = docA.fields[i].compareTo (docB.fields[i]);
146  48 break;
147  0 case SortField.AUTO:
148    // we cannot handle this - even if we determine the type of object (Float or
149    // Integer), we don't necessarily know how to compare them (both SCORE and
150    // FLOAT contain floats, but are sorted opposite of each other). Before
151    // we get here, each AUTO should have been replaced with its actual value.
152  0 throw new RuntimeException ("FieldDocSortedHitQueue cannot use an AUTO SortField");
153  0 default:
154  0 throw new RuntimeException ("invalid SortField type: "+type);
155    }
156  49213 if (fields[i].getReverse()) {
157  717 c = -c;
158    }
159    }
160   
161    // avoid random sort order that could lead to duplicates (bug #3