use std::collections::HashMap;
use icu_casemap::CaseMapperBorrowed;
use crate::casefold::simple_fold;
use crate::Workbook;
#[doc(hidden)]
pub struct SheetIndex {
by_folded: HashMap<String, usize>,
by_authored: HashMap<String, usize>,
folded: Vec<String>,
}
impl SheetIndex {
#[doc(hidden)]
pub fn build(workbook: &Workbook) -> Self {
let folder = CaseMapperBorrowed::new();
let sheets = workbook.sheets();
let folded: Vec<String> = sheets
.iter()
.map(|s| simple_fold(&folder, s.name()))
.collect();
let mut by_folded: HashMap<String, usize> = HashMap::with_capacity(sheets.len());
for (i, name) in folded.iter().enumerate() {
by_folded.entry(name.clone()).or_insert(i);
}
let mut by_authored: HashMap<String, usize> = HashMap::with_capacity(sheets.len());
for (i, sheet) in sheets.iter().enumerate() {
let resolved = by_folded[&folded[i]];
by_authored
.entry(sheet.name().to_owned())
.or_insert(resolved);
}
Self {
by_folded,
by_authored,
folded,
}
}
#[doc(hidden)]
pub fn index_of_folded(&self, folded: &str) -> Option<usize> {
self.by_folded.get(folded).copied()
}
#[doc(hidden)]
pub fn index_of_name(&self, name: &str) -> Option<usize> {
if let Some(i) = self.by_authored.get(name) {
return Some(*i);
}
let folder = CaseMapperBorrowed::new();
self.by_folded.get(&simple_fold(&folder, name)).copied()
}
#[doc(hidden)]
pub fn folded_name(&self, index: usize) -> &str {
&self.folded[index]
}
#[doc(hidden)]
pub fn folded_of_name(&self, name: &str) -> Option<&str> {
self.index_of_name(name).map(|i| self.folded_name(i))
}
#[doc(hidden)]
pub fn len(&self) -> usize {
self.folded.len()
}
#[doc(hidden)]
pub fn is_empty(&self) -> bool {
self.folded.is_empty()
}
}