#![allow(deprecated)]
#![allow(clippy::result_large_err)]
use numrs2::error::Result;
use numrs2::prelude::*;
use std::time::{Duration, Instant};
fn benchmark<F, R>(name: &str, runs: u32, f: F) -> Duration
where
F: Fn() -> R,
{
for _ in 0..5 {
let _ = f();
}
let start = Instant::now();
for _ in 0..runs {
let _ = f();
}
let elapsed = start.elapsed();
let avg_ns = elapsed.as_nanos() as f64 / runs as f64;
println!("{}: avg {:.2} ns per run ({} runs)", name, avg_ns, runs);
elapsed
}
fn main() -> Result<()> {
println!("NumRS2 Unique Function Benchmarks");
println!("================================");
let rng = RandomState::with_seed(42);
println!("\nPart 1: Small Array Benchmarks");
println!("-----------------------------");
let uniform_values = rng.uniform(0.0f64, 10.0f64, &[1000])?;
let int_values: Vec<i32> = uniform_values
.to_vec()
.iter()
.map(|&x| (x * 10.0f64).floor() as i32)
.collect();
let small_array = Array::from_vec(int_values).reshape(&[1000]);
benchmark("unique - small array", 1000, || {
unique(&small_array, None, None, None, None)
});
benchmark("unique - small array with all returns", 1000, || {
unique(&small_array, None, Some(true), Some(true), Some(true))
});
println!("\nPart 2: Large Array Benchmarks");
println!("-----------------------------");
let uniform_values_large = rng.uniform(0.0f64, 100.0f64, &[100000])?;
let int_values_large: Vec<i32> = uniform_values_large
.to_vec()
.iter()
.map(|&x| (x * 10.0f64).floor() as i32)
.collect();
let large_array = Array::from_vec(int_values_large).reshape(&[100000]);
benchmark("unique - large array", 100, || {
unique(&large_array, None, None, None, None)
});
benchmark("unique - large array with all returns", 100, || {
unique(&large_array, None, Some(true), Some(true), Some(true))
});
println!("\nPart 3: 2D Array Benchmarks");
println!("--------------------------");
let uniform_values_2d = rng.uniform(0.0f64, 10.0f64, &[1000, 5])?;
let int_values_2d: Vec<i32> = uniform_values_2d
.to_vec()
.iter()
.map(|&x| (x * 5.0f64).floor() as i32)
.collect();
let array_2d = Array::from_vec(int_values_2d).reshape(&[1000, 5]);
benchmark("unique - 2D array without axis", 1000, || {
unique(&array_2d, None, None, None, None)
});
benchmark("unique - 2D array with axis=0", 100, || {
unique(&array_2d, Some(0), None, None, None)
});
benchmark("unique - 2D array with axis=1", 100, || {
unique(&array_2d, Some(1), None, None, None)
});
println!("\nPart 4: String Array Benchmarks - Skipped");
println!("--------------------------------------");
println!("// Skipped: String doesn't implement Zero trait required by unique function");
println!("\nPart 5: Edge Cases");
println!("----------------");
let mostly_unique = Array::from_vec((0..10000).collect::<Vec<i32>>());
benchmark("unique - mostly unique elements", 100, || {
unique(&mostly_unique, None, None, None, None)
});
let all_same = Array::from_vec(vec![7; 10000]);
benchmark("unique - all identical elements", 100, || {
unique(&all_same, None, None, None, None)
});
println!("\nBenchmark complete!");
Ok(())
}