Skip to main content

bounded

Function bounded 

Source
pub fn bounded(
    key: &DomainKey,
    stream_id: u32,
    ordinal: u64,
    n: NonZeroU64,
) -> u64
Expand description

A uniform-ish draw in [0, n) by 64-bit multiply-shift.

bounded(..) = ((x as u128 * n.get() as u128) >> 64) as u64, where x is [assemble64] of the block at (key, stream_id, ordinal).

§This IS the contracted derivation

Its non-uniformity is below 2⁻⁴⁴ for every range this protocol reaches (class buckets ≤ 587 rows, pair spaces ≤ ~10⁵), and it is branch-free and index-pure. Contract assumption A3 records that as the derivation itself, not as an approximation of some exact-uniform alternative — so a future reader does not “correct” it into rejection sampling and change every sampled identity in the process.

Modulo is FORBIDDEN: its bias at the top of the range is real and, worse, unauditable — two implementations can both look correct and disagree. Float scaling is FORBIDDEN: a 23-bit mantissa cannot address a bucket beyond 2²⁴ without collisions.

§A zero bound is unrepresentable

n is a NonZeroU64, so bounded(.., 0) is a type error rather than a silent constant or a fault:

ⓘ
use aprender_contrastive_data::rng::{bounded, derive_key};

let key = derive_key(13, "select/0");
let _ = bounded(&key, 0, 0, 0u64);

The same call with a real bound compiles, which is what stops the block above from being green for an unrelated reason:

use core::num::NonZeroU64;
use aprender_contrastive_data::rng::{bounded, derive_key};

let key = derive_key(13, "select/0");
let one = NonZeroU64::new(1).expect("1 is not zero");
assert_eq!(bounded(&key, 0, 0, one), 0);