use std::collections::BTreeMap;
use criterion::{black_box, criterion_group, criterion_main, Criterion};
use rand::{Rng, SeedableRng};
use rand::seq::SliceRandom;
use hibit_tree::{HierarchyIndex, ReqDefault};
use hibit_tree::config::_64bit;
use hibit_tree::HibitTree;
use hibit_tree::Tree;
const RANGE: usize = 260_000;
const COUNT: usize = 4000;
#[derive(Default, Clone)]
struct DataBlock(u64);
type Map = nohash_hasher::IntMap<u32, DataBlock>;
type BTree = BTreeMap<u32, DataBlock>;
type BlockArrayNew = Tree<DataBlock, _64bit<4>, ReqDefault>;
fn array_new_get(array: &BlockArrayNew, indices: &[usize]) -> u64 {
let mut s = 0;
for &i in indices{
unsafe{
s += array.get(HierarchyIndex::new_unchecked(i))
.unwrap_or(&DataBlock(0)).0;
}
}
s
}
fn array_new_get_or_default(array: &BlockArrayNew, indices: &[usize]) -> u64 {
let mut s = 0;
for &i in indices{
unsafe{
s += array.get_or_default(HierarchyIndex::new_unchecked(i)).0;
}
}
s
}
fn hashmap_get(array: &Map, indices: &[usize]) -> u64 {
let mut s = 0;
for i in indices{
s += array.get(&(*i as _)).unwrap_or(&DataBlock(0)).0;
}
s
}
fn btree_get(array: &BTree, indices: &[usize]) -> u64 {
let mut s = 0;
for i in indices{
s += array.get(&(*i as _)).unwrap_or(&DataBlock(0)).0;
}
s
}
pub fn bench_iter(c: &mut Criterion) {
let mut new_array = BlockArrayNew::new();
let mut new_array2 = BlockArrayNew::new();
let mut hashmap = Map::default();
let mut btree = BTree::default();
let mut rng = rand::rngs::StdRng::seed_from_u64(0xe15bb9db3dee3a0f);
let mut random_indices = Vec::new();
for _ in 0..COUNT {
let v = rng.gen_range(0..RANGE);
random_indices.push(v);
new_array.insert(v, DataBlock(v as _));
new_array2.insert(v, DataBlock(v as _));
hashmap.insert(v as _, DataBlock(v as u64));
btree.insert(v as _, DataBlock(v as u64));
}
random_indices.shuffle(&mut rng);
c.bench_function("new array2", |b| b.iter(|| array_new_get_or_default(black_box(&new_array2), black_box(&random_indices))));
c.bench_function("new array", |b| b.iter(|| array_new_get(black_box(&new_array), black_box(&random_indices))));
c.bench_function("hashmap", |b| b.iter(|| hashmap_get(black_box(&hashmap), black_box(&random_indices))));
c.bench_function("btree", |b| b.iter(|| btree_get(black_box(&btree), black_box(&random_indices))));
}
criterion_group!(benches_iter, bench_iter);
criterion_main!(benches_iter);