bench_min_rotational_hamming/
bench_min_rotational_hamming.rs1use std::hint::black_box;
11use std::time::Instant;
12
13use ring_seq::AsCircular;
14
15fn rotated(a: &[u32], k: usize) -> Vec<u32> {
16 let n = a.len();
17 (0..n).map(|i| a[(i + k) % n]).collect()
18}
19
20fn one_off(a: &[u32]) -> Vec<u32> {
21 let mut v = a.to_vec();
22 if !v.is_empty() {
23 v[0] = v[0].wrapping_add(1);
24 }
25 v
26}
27
28fn reversed(a: &[u32]) -> Vec<u32> {
29 let mut v = a.to_vec();
30 v.reverse();
31 v
32}
33
34fn bench_case(label: &str, n: usize, iters: u64, a: &[u32], b: &[u32]) {
35 for _ in 0..(iters / 10).max(1) {
37 black_box(a.circular().min_rotational_hamming_distance(black_box(b)));
38 }
39 let start = Instant::now();
40 let mut acc: usize = 0;
41 for _ in 0..iters {
42 acc = acc.wrapping_add(black_box(
43 a.circular().min_rotational_hamming_distance(black_box(b)),
44 ));
45 }
46 let elapsed = start.elapsed();
47 let ns_per_op = elapsed.as_nanos() as f64 / iters as f64;
48 println!(
49 "{:<10} n={:<5} iters={:<10} total={:>10.3?} ns/op={:>12.0} (acc={})",
50 label, n, iters, elapsed, ns_per_op, acc
51 );
52}
53
54fn iters_for(n: usize) -> u64 {
55 match n {
56 16 => 1_000_000,
57 256 => 10_000,
58 4096 => 50,
59 _ => 1_000,
60 }
61}
62
63fn main() {
64 for &n in &[16usize, 256, 4096] {
65 let base: Vec<u32> = (0..n as u32).collect();
66 let rot = rotated(&base, n / 3);
67 let off = one_off(&base);
68 let rev = reversed(&base);
69 let iters = iters_for(n);
70
71 bench_case("rotation", n, iters, &base, &rot);
72 bench_case("oneOff ", n, iters, &base, &off);
73 bench_case("reversed", n, iters, &base, &rev);
74 println!();
75 }
76}