use crate::constants::{AXON_SENTINEL, V_SEG};
use crate::types::AxonHead;
#[inline(always)]
pub const fn is_in_active_tail(head_idx: u32, segment_idx: u32, propagation_length: u8) -> bool {
let dist = head_idx.wrapping_sub(segment_idx);
dist < (propagation_length as u32)
}
#[inline]
pub fn is_segment_active(axon_head: AxonHead, segment_idx: u32, propagation_length: u32) -> bool {
if axon_head == AXON_SENTINEL {
return false;
}
axon_head.wrapping_sub(segment_idx) < propagation_length
}
#[inline]
pub fn initial_axon_head(length_segments: u32) -> AxonHead {
AXON_SENTINEL.wrapping_sub(length_segments * V_SEG)
}
#[cfg(test)]
#[path = "test_signal.rs"]
mod test_signal;
#[cfg(test)]
#[path = "test_train_model.rs"]
mod test_train_model;
#[cfg(test)]
mod tests {
use super::*;
use crate::constants::AXON_SENTINEL;
#[test]
fn test_active_tail_normal_overlap() {
assert!(is_in_active_tail(10, 8, 3));
assert!(is_in_active_tail(10, 10, 3));
assert!(is_in_active_tail(10, 9, 3));
}
#[test]
fn test_active_tail_outside() {
assert!(!is_in_active_tail(10, 7, 3));
assert!(!is_in_active_tail(10, 0, 3));
}
#[test]
fn test_sentinel_edge_case() {
assert!(!is_in_active_tail(AXON_SENTINEL, 5, 3));
assert!(!is_in_active_tail(AXON_SENTINEL, 0, 255));
assert!(!is_in_active_tail(AXON_SENTINEL, 1000, 100));
}
#[test]
fn test_active_tail_zero_propagation() {
assert!(!is_in_active_tail(10, 10, 0));
assert!(!is_in_active_tail(10, 9, 0));
}
}