pub(crate) struct LabelGen {
counter: u32,
}
impl LabelGen {
pub(crate) fn new() -> Self {
LabelGen { counter: 0 }
}
pub(crate) fn fresh(&mut self, prefix: &str) -> String {
let label = format!(".L{prefix}_{}", self.counter);
self.counter += 1;
label
}
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn fresh_numbers_labels_monotonically_from_zero() {
let mut lg = LabelGen::new();
assert_eq!(lg.fresh("if_end"), ".Lif_end_0");
assert_eq!(lg.fresh("if_end"), ".Lif_end_1");
}
#[test]
fn the_counter_is_shared_across_prefixes() {
let mut lg = LabelGen::new();
assert_eq!(lg.fresh("if_else"), ".Lif_else_0");
assert_eq!(lg.fresh("while_test"), ".Lwhile_test_1");
assert_eq!(lg.fresh("if_else"), ".Lif_else_2");
}
#[test]
fn a_fresh_generator_restarts_at_zero() {
let mut a = LabelGen::new();
let _ = a.fresh("and_done");
let _ = a.fresh("and_done");
let mut b = LabelGen::new();
assert_eq!(b.fresh("and_done"), ".Land_done_0");
}
}