mod fx_fx;
mod fx_q;
use crate::UInt;
pub use fx_fx::{to_Fx, Fx};
pub use fx_q::{to_Q, Q};
pub trait FixedPoint {
fn eval(&self) -> f64;
}
fn debug_print(val: UInt, m: i32, b: i32, is_exact: bool) -> String {
const ANSI_RESET_COLOR: &str = "\x1b[0m";
const ANSI_RED: &str = "\x1b[37;41m";
const ANSI_BLACK: &str = "\x1b[37;40m"; const ANSI_MAGENTA: &str = "\x1b[45m";
let bits = format!("{:0width$b}", val, width = (b) as usize);
let dots = if is_exact { "" } else { "..." };
let ans = format!(
"{ANSI_RED}{sign}{ANSI_MAGENTA}{int}{ANSI_BLACK}{frac}{dots}{ANSI_RESET_COLOR}",
sign = &bits[..1],
int = &bits[1..(m + 1) as usize],
frac = &bits[(m + 1) as usize..],
);
ans
}
#[cfg(test)]
mod test {
use crate::fixed_point::{Fx, Q};
#[test]
fn test_neg() {
let fx1 = Fx::new(0b0_000_0, 3, 5, true); let fx1_neg = Fx::new(0b0_000_0, 3, 5, true); assert_eq!(-fx1, fx1_neg);
}
#[test]
fn test_neg_zero() {
let fx1 = Fx::new(
0b0_001_000110110011101111100011101110111111010001000110100,
3,
55,
true,
); let fx1_neg = Fx::new(
0b1_110_111001001100010000011100010001000000101110111001100,
3,
55,
true,
); assert_eq!(-fx1, fx1_neg);
}
#[test]
fn test_sub() {
let fx1 = Fx::new(0b0_111_1, 3, 5, true); let fx2 = Fx::new(0b0_111_0, 3, 5, true); let fx3 = Fx::new(0b0_000_1, 3, 5, true); assert_eq!(fx1 - fx2, fx3);
}
#[test]
fn test_mul() {
let fx1 = Fx::new(0b0_000000111_10, 9, 12, true); let fx2 = Fx::new(0b0_000000011_10, 9, 12, true); let fx3 = Fx::new(0b0_000011010_01, 9, 12, true); assert_eq!(fx1 * fx2, fx3);
}
#[test]
fn test_shift() {
let fx1 = Q::new(0b1111, 3, 1, true);
assert_eq!(fx1 << 1, Q::new(0b1110, 3, 1, true));
assert_eq!(fx1 << 2, Q::new(0b1100, 3, 1, true));
assert_eq!(fx1 << 3, Q::new(0b1000, 3, 1, true));
assert_eq!(fx1 >> 1, Q::new(0b0111, 3, 1, true));
}
}