Introduce an optimization when the searchable attributes are ordered

This commit is contained in:
Clément Renault 2020-11-03 19:59:09 +01:00
parent 01c4f5abcd
commit a31db33e93
No known key found for this signature in database
GPG Key ID: 92ADA4E935E71FA4

View File

@ -69,34 +69,50 @@ impl<'a, 't, 'u, 'i> Settings<'a, 't, 'u, 'i> {
let result = match value { let result = match value {
Some(fields_names) => { Some(fields_names) => {
// We create or generate the fields ids corresponding to those names. let mut fields_ids_map = current_fields_ids_map.clone();
let mut fields_ids_map = FieldsIdsMap::new(); let searchable_fields: Vec<_> =
let mut searchable_fields = Vec::new(); fields_names.iter()
for name in fields_names { .map(|name| fields_ids_map.insert(name))
let id = fields_ids_map.insert(&name).context("field id limit reached")?; .collect::<Option<Vec<_>>>()
searchable_fields.push(id); .context("field id limit reached")?;
// If the searchable fields are ordered we don't have to generate a new `FieldsIdsMap`.
if searchable_fields.windows(2).all(|win| win[0] < win[1]) {
(
fields_ids_map,
Some(searchable_fields),
current_displayed_fields.map(ToOwned::to_owned),
)
} else {
// We create or generate the fields ids corresponding to those names.
let mut fields_ids_map = FieldsIdsMap::new();
let mut searchable_fields = Vec::new();
for name in fields_names {
let id = fields_ids_map.insert(&name).context("field id limit reached")?;
searchable_fields.push(id);
}
// We complete the new FieldsIdsMap with the previous names.
for (_id, name) in current_fields_ids_map.iter() {
fields_ids_map.insert(name).context("field id limit reached")?;
}
// We must also update the displayed fields according to the new `FieldsIdsMap`.
let displayed_fields = match current_displayed_fields {
Some(fields) => {
let mut displayed_fields = Vec::new();
for id in fields {
let name = current_fields_ids_map.name(*id).unwrap();
let id = fields_ids_map.id(name).context("field id limit reached")?;
displayed_fields.push(id);
}
Some(displayed_fields)
},
None => None,
};
(fields_ids_map, Some(searchable_fields), displayed_fields)
} }
// We complete the new FieldsIdsMap with the previous names.
for (_id, name) in current_fields_ids_map.iter() {
fields_ids_map.insert(name).context("field id limit reached")?;
}
// We must also update the displayed fields according to the new `FieldsIdsMap`.
let displayed_fields = match current_displayed_fields {
Some(fields) => {
let mut displayed_fields = Vec::new();
for id in fields {
let name = current_fields_ids_map.name(*id).unwrap();
let id = fields_ids_map.id(name).context("field id limit reached")?;
displayed_fields.push(id);
}
Some(displayed_fields)
},
None => None,
};
(fields_ids_map, Some(searchable_fields), displayed_fields)
}, },
None => ( None => (
current_fields_ids_map.clone(), current_fields_ids_map.clone(),