#[derive(Clone, Debug, Default)]
pub struct ModRange {
slot: u64,
interval: u64,
shards: usize,
}
impl ModRange {
pub fn from(num: Option<u64>, shards: usize) -> Self {
let slot = num.unwrap_or(256);
assert!(shards > 0 && slot >= shards as u64);
ModRange {
slot,
interval: slot / shards as u64,
shards,
}
}
pub fn index(&self, hash: i64) -> usize {
let mut val = hash.wrapping_rem(self.slot as i64);
if val < 0 {
tracing::warn!("found negative modrange pre hash:{:?}", val);
val = val.wrapping_abs();
}
let rs = val as u64 / self.interval;
if rs >= self.shards as u64 {
tracing::warn!(
"found modrange slot out of bound, rs:{}, shards:{}",
rs,
self.shards
);
return self.shards - 1;
}
rs as usize
}
}