use akar_common::types::Value;
const RADIX_BITS: u32 = 8;
const RADIX_BUCKETS: usize = 1 << RADIX_BITS;
pub fn radix_sort_indices(indices: &mut [usize], keys: &[i64]) {
let len = indices.len();
if len < 2 {
return;
}
let mut tmp_indices = vec![0usize; len];
let mut tmp_keys = vec![0u64; len];
for (i, &k) in keys.iter().enumerate() {
tmp_keys[i] = (k as u64) ^ (1u64 << 63);
}
let mut counts = [0u32; RADIX_BUCKETS];
for pass in 0..8u32 {
counts.fill(0);
for &k in &tmp_keys {
let bucket = ((k >> (pass * RADIX_BITS)) & 0xFF) as usize;
counts[bucket] += 1;
}
let mut total = 0u32;
for c in counts.iter_mut() {
let prev = *c;
*c = total;
total += prev;
}
let mut next_keys = vec![0u64; len];
for (i, &k) in tmp_keys.iter().enumerate() {
let bucket = ((k >> (pass * RADIX_BITS)) & 0xFF) as usize;
let pos = counts[bucket] as usize;
tmp_indices[pos] = indices[i];
next_keys[pos] = k;
counts[bucket] += 1;
}
indices.copy_from_slice(&tmp_indices);
tmp_keys = next_keys;
}
}
pub fn is_radix_eligible(values: &[(Value, bool)]) -> bool {
values.iter().all(|(v, _)| matches!(v, Value::Int64(_) | Value::Null))
}