@@ -12,6 +12,7 @@ use crate::heed_codec::ByteSliceRefCodec;
1212use crate :: search:: criteria:: { resolve_query_tree, CriteriaBuilder , InitialCandidates } ;
1313use crate :: search:: facet:: { ascending_facet_sort, descending_facet_sort} ;
1414use crate :: search:: query_tree:: Operation ;
15+ use crate :: search:: CriterionImplementationStrategy ;
1516use crate :: { FieldId , Index , Result } ;
1617
1718/// Threshold on the number of candidates that will make
@@ -29,6 +30,7 @@ pub struct AscDesc<'t> {
2930 allowed_candidates : RoaringBitmap ,
3031 initial_candidates : InitialCandidates ,
3132 faceted_candidates : RoaringBitmap ,
33+ implementation_strategy : CriterionImplementationStrategy ,
3234 parent : Box < dyn Criterion + ' t > ,
3335}
3436
@@ -38,17 +40,19 @@ impl<'t> AscDesc<'t> {
3840 rtxn : & ' t heed:: RoTxn ,
3941 parent : Box < dyn Criterion + ' t > ,
4042 field_name : String ,
43+ implementation_strategy : CriterionImplementationStrategy ,
4144 ) -> Result < Self > {
42- Self :: new ( index, rtxn, parent, field_name, true )
45+ Self :: new ( index, rtxn, parent, field_name, true , implementation_strategy )
4346 }
4447
4548 pub fn desc (
4649 index : & ' t Index ,
4750 rtxn : & ' t heed:: RoTxn ,
4851 parent : Box < dyn Criterion + ' t > ,
4952 field_name : String ,
53+ implementation_strategy : CriterionImplementationStrategy ,
5054 ) -> Result < Self > {
51- Self :: new ( index, rtxn, parent, field_name, false )
55+ Self :: new ( index, rtxn, parent, field_name, false , implementation_strategy )
5256 }
5357
5458 fn new (
@@ -57,6 +61,7 @@ impl<'t> AscDesc<'t> {
5761 parent : Box < dyn Criterion + ' t > ,
5862 field_name : String ,
5963 is_ascending : bool ,
64+ implementation_strategy : CriterionImplementationStrategy ,
6065 ) -> Result < Self > {
6166 let fields_ids_map = index. fields_ids_map ( rtxn) ?;
6267 let field_id = fields_ids_map. id ( & field_name) ;
@@ -82,6 +87,7 @@ impl<'t> AscDesc<'t> {
8287 allowed_candidates : RoaringBitmap :: new ( ) ,
8388 faceted_candidates,
8489 initial_candidates : InitialCandidates :: Estimated ( RoaringBitmap :: new ( ) ) ,
90+ implementation_strategy,
8591 parent,
8692 } )
8793 }
@@ -149,6 +155,7 @@ impl<'t> Criterion for AscDesc<'t> {
149155 field_id,
150156 self . is_ascending ,
151157 candidates & & self . faceted_candidates ,
158+ self . implementation_strategy ,
152159 ) ?,
153160 None => Box :: new ( std:: iter:: empty ( ) ) ,
154161 } ;
@@ -170,6 +177,51 @@ impl<'t> Criterion for AscDesc<'t> {
170177 }
171178}
172179
180+ fn facet_ordered_iterative < ' t > (
181+ index : & ' t Index ,
182+ rtxn : & ' t heed:: RoTxn ,
183+ field_id : FieldId ,
184+ is_ascending : bool ,
185+ candidates : RoaringBitmap ,
186+ ) -> Result < Box < dyn Iterator < Item = heed:: Result < RoaringBitmap > > + ' t > > {
187+ let number_iter = iterative_facet_number_ordered_iter (
188+ index,
189+ rtxn,
190+ field_id,
191+ is_ascending,
192+ candidates. clone ( ) ,
193+ ) ?;
194+ let string_iter =
195+ iterative_facet_string_ordered_iter ( index, rtxn, field_id, is_ascending, candidates) ?;
196+ Ok ( Box :: new ( number_iter. chain ( string_iter) . map ( Ok ) ) as Box < dyn Iterator < Item = _ > > )
197+ }
198+
199+ fn facet_ordered_set_based < ' t > (
200+ index : & ' t Index ,
201+ rtxn : & ' t heed:: RoTxn ,
202+ field_id : FieldId ,
203+ is_ascending : bool ,
204+ candidates : RoaringBitmap ,
205+ ) -> Result < Box < dyn Iterator < Item = heed:: Result < RoaringBitmap > > + ' t > > {
206+ let make_iter = if is_ascending { ascending_facet_sort } else { descending_facet_sort } ;
207+
208+ let number_iter = make_iter (
209+ rtxn,
210+ index. facet_id_f64_docids . remap_key_type :: < FacetGroupKeyCodec < ByteSliceRefCodec > > ( ) ,
211+ field_id,
212+ candidates. clone ( ) ,
213+ ) ?;
214+
215+ let string_iter = make_iter (
216+ rtxn,
217+ index. facet_id_string_docids . remap_key_type :: < FacetGroupKeyCodec < ByteSliceRefCodec > > ( ) ,
218+ field_id,
219+ candidates,
220+ ) ?;
221+
222+ Ok ( Box :: new ( number_iter. chain ( string_iter) ) )
223+ }
224+
173225/// Returns an iterator over groups of the given candidates in ascending or descending order.
174226///
175227/// It will either use an iterative or a recursive method on the whole facet database depending
@@ -180,36 +232,22 @@ fn facet_ordered<'t>(
180232 field_id : FieldId ,
181233 is_ascending : bool ,
182234 candidates : RoaringBitmap ,
235+ implementation_strategy : CriterionImplementationStrategy ,
183236) -> Result < Box < dyn Iterator < Item = heed:: Result < RoaringBitmap > > + ' t > > {
184- if candidates. len ( ) <= CANDIDATES_THRESHOLD {
185- let number_iter = iterative_facet_number_ordered_iter (
186- index,
187- rtxn,
188- field_id,
189- is_ascending,
190- candidates. clone ( ) ,
191- ) ?;
192- let string_iter =
193- iterative_facet_string_ordered_iter ( index, rtxn, field_id, is_ascending, candidates) ?;
194- Ok ( Box :: new ( number_iter. chain ( string_iter) . map ( Ok ) ) as Box < dyn Iterator < Item = _ > > )
195- } else {
196- let make_iter = if is_ascending { ascending_facet_sort } else { descending_facet_sort } ;
197-
198- let number_iter = make_iter (
199- rtxn,
200- index. facet_id_f64_docids . remap_key_type :: < FacetGroupKeyCodec < ByteSliceRefCodec > > ( ) ,
201- field_id,
202- candidates. clone ( ) ,
203- ) ?;
204-
205- let string_iter = make_iter (
206- rtxn,
207- index. facet_id_string_docids . remap_key_type :: < FacetGroupKeyCodec < ByteSliceRefCodec > > ( ) ,
208- field_id,
209- candidates,
210- ) ?;
211-
212- Ok ( Box :: new ( number_iter. chain ( string_iter) ) )
237+ match implementation_strategy {
238+ CriterionImplementationStrategy :: OnlyIterative => {
239+ facet_ordered_iterative ( index, rtxn, field_id, is_ascending, candidates)
240+ }
241+ CriterionImplementationStrategy :: OnlySetBased => {
242+ facet_ordered_set_based ( index, rtxn, field_id, is_ascending, candidates)
243+ }
244+ CriterionImplementationStrategy :: Dynamic => {
245+ if candidates. len ( ) <= CANDIDATES_THRESHOLD {
246+ facet_ordered_iterative ( index, rtxn, field_id, is_ascending, candidates)
247+ } else {
248+ facet_ordered_set_based ( index, rtxn, field_id, is_ascending, candidates)
249+ }
250+ }
213251 }
214252}
215253
0 commit comments