#[derive(Debug, Clone)]
pub struct BlockIdentity {
pub block_name: String,
pub original_dim: usize,
pub effective_dim: usize,
pub design_range_rank: usize,
}
#[derive(Debug, Clone)]
pub struct AliasedPair {
pub block_a: String,
pub block_b: String,
pub direction_a: usize,
pub direction_b: usize,
pub overlap: f64,
pub bias_shift: f64,
}
#[derive(Debug, Clone)]
pub struct DroppedColumn {
pub block: String,
pub column: usize,
pub reason: String,
}
#[derive(Debug, Clone)]
pub struct IdentifiabilityAudit {
pub blocks: Vec<BlockIdentity>,
pub aliased_pairs: Vec<AliasedPair>,
pub dropped_columns: Vec<DroppedColumn>,
pub fatal: bool,
pub summary: String,
}
#[derive(Debug, Clone)]
pub struct MapUniquenessError {
pub message: String,
pub dominant_block: String,
pub null_direction_index: usize,
pub penalty_quadratic_form: f64,
}
impl std::fmt::Display for MapUniquenessError {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
write!(f, "{}", self.message)
}
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn map_uniqueness_error_display_uses_message_field() {
let err = MapUniquenessError {
message: "null direction in block_x".to_string(),
dominant_block: "block_x".to_string(),
null_direction_index: 2,
penalty_quadratic_form: 1e-18,
};
assert_eq!(err.to_string(), "null direction in block_x");
}
#[test]
fn map_uniqueness_error_fields_accessible() {
let err = MapUniquenessError {
message: "msg".to_string(),
dominant_block: "blk".to_string(),
null_direction_index: 5,
penalty_quadratic_form: 0.0,
};
assert_eq!(err.dominant_block, "blk");
assert_eq!(err.null_direction_index, 5);
assert_eq!(err.penalty_quadratic_form, 0.0);
}
#[test]
fn identifiability_audit_fatal_field_readable() {
let audit = IdentifiabilityAudit {
blocks: vec![],
aliased_pairs: vec![],
dropped_columns: vec![],
fatal: true,
summary: "summary text".to_string(),
};
assert!(audit.fatal);
assert_eq!(audit.summary, "summary text");
}
#[test]
fn block_identity_fields_accessible() {
let bi = BlockIdentity {
block_name: "smooth_1".to_string(),
original_dim: 5,
effective_dim: 4,
design_range_rank: 4,
};
assert_eq!(bi.block_name, "smooth_1");
assert_eq!(bi.original_dim, 5);
assert_eq!(bi.effective_dim, 4);
}
#[test]
fn aliased_pair_overlap_in_range() {
let pair = AliasedPair {
block_a: "a".to_string(),
block_b: "b".to_string(),
direction_a: 0,
direction_b: 1,
overlap: 0.95,
bias_shift: 0.0,
};
assert!(pair.overlap >= 0.0 && pair.overlap <= 1.0);
assert_eq!(pair.block_a, "a");
}
}