use approx::assert_relative_eq;
use spirix::*;
#[cfg(test)]
mod basic_operations {
use super::*;
#[test]
fn test_scalar_creation_and_conversion() {
let a = ScalarF5E3::from(42);
let b = ScalarF5E3::from(-17);
assert!(a.is_normal());
assert!(b.is_normal());
assert!(a.is_positive());
assert!(b.is_negative());
let pi = ScalarF5E3::from(3.14159);
let e = ScalarF5E3::from(2.71828);
assert!(pi.is_normal());
assert!(e.is_normal());
let zero = ScalarF5E3::ZERO;
let one = ScalarF5E3::ONE;
let pi_const = ScalarF5E3::PI;
let e_const = ScalarF5E3::E;
assert!(zero.is_zero());
assert!(one.is_normal());
assert!(pi_const.is_normal());
assert!(e_const.is_normal());
}
#[test]
fn test_basic_arithmetic() {
let a = ScalarF5E3::from(7);
let b = ScalarF5E3::from(3);
let sum = a + b;
assert!(sum.is_normal());
let sum_f32: f32 = sum.into();
assert_relative_eq!(sum_f32, 10.0, epsilon = 1e-5);
let diff = a - b;
assert!(diff.is_normal());
let diff_f32: f32 = diff.into();
assert_relative_eq!(diff_f32, 4.0, epsilon = 1e-5);
let product = a * b;
assert!(product.is_normal());
let product_f32: f32 = product.into();
assert_relative_eq!(product_f32, 21.0, epsilon = 1e-5);
let quotient = a / b;
assert!(quotient.is_normal());
let quotient_f32: f32 = quotient.into();
assert_relative_eq!(quotient_f32, 7.0 / 3.0, epsilon = 1e-5);
let neg_a = -a;
assert!(neg_a.is_normal());
assert!(neg_a.is_negative());
let neg_a_f32: f32 = neg_a.into();
assert_relative_eq!(neg_a_f32, -7.0, epsilon = 1e-5);
}
#[test]
fn test_zero_operations() {
let zero = ScalarF5E3::ZERO;
let five = ScalarF5E3::from(5);
let result = five + zero;
assert!(result.is_normal());
let result_f32: f32 = result.into();
assert_relative_eq!(result_f32, 5.0, epsilon = 1e-5);
let result2 = zero + five;
assert!(result2.is_normal());
let result2_f32: f32 = result2.into();
assert_relative_eq!(result2_f32, 5.0, epsilon = 1e-5);
let result3 = five * zero;
assert!(result3.is_zero());
let result4 = zero * five;
assert!(result4.is_zero());
let div_by_zero = five / zero;
assert!(!div_by_zero.is_normal());
assert!(!div_by_zero.is_finite());
println!("Division by zero result: {:?}", div_by_zero);
}
#[test]
fn test_integer_detection() {
assert!(ScalarF5E3::from(42).is_integer());
assert!(ScalarF5E3::from(0).is_integer());
let neg_int = ScalarF5E3::from(-17);
println!(
"ScalarF5E3::from(-17).is_integer() = {}",
neg_int.is_integer()
);
assert!(!ScalarF5E3::from(3.14).is_integer());
}
}
#[cfg(test)]
mod mathematical_functions {
use super::*;
#[test]
fn test_trigonometric_functions() {
let pi_half: ScalarF5E3 = ScalarF5E3::PI / 2.0;
let sin_pi_half = pi_half.sin();
assert!(sin_pi_half.is_normal());
let sin_f32: f32 = sin_pi_half.into();
assert_relative_eq!(sin_f32, 1.0, epsilon = 1e-4);
let cos_zero = ScalarF5E3::ZERO.cos();
assert!(cos_zero.is_normal());
let cos_f32: f32 = cos_zero.into();
assert_relative_eq!(cos_f32, 1.0, epsilon = 1e-4);
let x = ScalarF5E3::from(0.5);
let sin_x = x.sin();
let cos_x = x.cos();
if sin_x.is_normal() && cos_x.is_normal() {
let sin_squared = sin_x.square();
let cos_squared = cos_x.square();
let identity = sin_squared + cos_squared;
if identity.is_normal() {
let identity_val: f32 = identity.into();
assert_relative_eq!(identity_val, 1.0, epsilon = 1e-3);
}
}
}
#[test]
fn test_exponential_and_logarithmic() {
let exp_result = ScalarF5E3::from(1).exp();
assert!(exp_result.is_normal());
let exp_f32: f32 = exp_result.into();
assert_relative_eq!(exp_f32, std::f32::consts::E, epsilon = 1e-4);
let ln_e = ScalarF5E3::E.ln();
assert!(ln_e.is_normal());
let ln_f32: f32 = ln_e.into();
assert_relative_eq!(ln_f32, 1.0, epsilon = 1e-4);
let powb_3 = ScalarF5E3::from(3).powb();
assert!(powb_3.is_normal());
let powb_f32: f32 = powb_3.into();
assert_relative_eq!(powb_f32, 8.0, epsilon = 1e-4);
}
#[test]
fn test_power_functions() {
let base = ScalarF5E3::from(2);
let exp = ScalarF5E3::from(3);
let result = base.pow(exp);
assert!(result.is_normal());
let result_f32: f32 = result.into();
assert_relative_eq!(result_f32, 8.0, epsilon = 1e-5);
let square = base.square();
assert!(square.is_normal());
let square_f32: f32 = square.into();
assert_relative_eq!(square_f32, 4.0, epsilon = 1e-5);
let sqrt_val = ScalarF5E3::from(9).sqrt();
assert!(sqrt_val.is_normal());
let sqrt_f32: f32 = sqrt_val.into();
assert_relative_eq!(sqrt_f32, 3.0, epsilon = 1e-5);
}
}
#[cfg(test)]
mod complex_numbers {
use super::*;
#[test]
fn test_circle_creation() {
let z1 = CircleF5E3::from((3.0, 4.0));
assert!(z1.is_normal());
let real = z1.r();
let imag = z1.i();
let real_f32: f32 = real.into();
let imag_f32: f32 = imag.into();
assert_relative_eq!(real_f32, 3.0, epsilon = 1e-5);
assert_relative_eq!(imag_f32, 4.0, epsilon = 1e-5);
}
#[test]
fn test_complex_constants() {
let zero = CircleF5E3::ZERO;
let one = CircleF5E3::ONE;
let pos_i = CircleF5E3::POS_I;
assert!(zero.is_zero());
assert!(one.is_normal());
assert!(pos_i.is_normal());
let one_real: f32 = one.r().into();
let one_imag: f32 = one.i().into();
assert_relative_eq!(one_real, 1.0, epsilon = 1e-6);
assert_relative_eq!(one_imag, 0.0, epsilon = 1e-6);
let pos_i_real: f32 = pos_i.r().into();
let pos_i_imag: f32 = pos_i.i().into();
assert_relative_eq!(pos_i_real, 0.0, epsilon = 1e-6);
assert_relative_eq!(pos_i_imag, 1.0, epsilon = 1e-6);
}
#[test]
fn test_complex_arithmetic_corrected() {
let z1 = CircleF5E3::from((3.0, 4.0)); let z2 = CircleF5E3::from((1.0, -2.0));
let sum = z1 + z2;
assert!(sum.is_normal());
let sum_real: f32 = sum.r().into();
let sum_imag: f32 = sum.i().into();
assert_relative_eq!(sum_real, 4.0, epsilon = 1e-5);
assert_relative_eq!(sum_imag, 2.0, epsilon = 1e-5);
let diff = z1 - z2;
assert!(diff.is_normal());
let diff_real: f32 = diff.r().into();
let diff_imag: f32 = diff.i().into();
assert_relative_eq!(diff_real, 2.0, epsilon = 1e-5);
assert_relative_eq!(diff_imag, 6.0, epsilon = 1e-5);
let product = z1 * z2;
assert!(product.is_normal());
let prod_real: f32 = product.r().into();
let prod_imag: f32 = product.i().into();
println!(
"Complex multiplication result: {} + {}i",
prod_real, prod_imag
);
assert!(prod_real.is_finite());
assert!(prod_imag.is_finite());
}
#[test]
fn test_complex_magnitude() {
let z = CircleF5E3::from((3.0, 4.0));
let mag = z.magnitude();
assert!(mag.is_normal());
let mag_f32: f32 = mag.into();
assert_relative_eq!(mag_f32, 5.0, epsilon = 1e-5);
let mag_sq = z.magnitude_squared();
assert!(mag_sq.is_normal());
let mag_sq_f32: f32 = mag_sq.into();
assert_relative_eq!(mag_sq_f32, 25.0, epsilon = 1e-5);
}
#[test]
fn test_complex_conjugate() {
let z = CircleF5E3::from((3.0, 4.0)); let conj = z.conjugate();
assert!(conj.is_normal());
let conj_real: f32 = conj.r().into();
let conj_imag: f32 = conj.i().into();
assert_relative_eq!(conj_real, 3.0, epsilon = 1e-5);
assert_relative_eq!(conj_imag, -4.0, epsilon = 1e-5);
}
}
#[cfg(test)]
mod bitwise_operations {
use super::*;
#[test]
fn test_bitwise_behavior() {
let a = ScalarF5E3::from(0b1010); let b = ScalarF5E3::from(0b1100);
let and_result = a & b;
assert!(and_result.is_normal());
let and_val: i32 = and_result.into();
assert!(and_val >= 0); println!("Bitwise AND result: {}", and_val);
let or_result = a | b;
let or_val: i32 = or_result.into();
println!("Bitwise OR result: {}", or_val);
let xor_result = a ^ b;
let xor_val: i32 = xor_result.into();
println!("Bitwise XOR result: {}", xor_val);
}
}
#[cfg(test)]
mod state_testing {
use super::*;
#[test]
fn test_value_states() {
let normal = ScalarF5E3::from(42);
let zero = ScalarF5E3::ZERO;
assert!(normal.is_normal());
assert!(normal.is_finite());
assert!(normal.is_positive());
assert!(!normal.is_negative());
assert!(!normal.is_zero());
assert!(!zero.is_normal());
assert!(zero.is_finite());
assert!(!zero.is_positive());
assert!(!zero.is_negative());
assert!(zero.is_zero());
}
#[test]
fn test_escaped_values() {
let max_val = ScalarF5E3::MAX;
let large: ScalarF5E3 = max_val * 2.0;
if large.exploded() {
assert!(large.is_positive());
assert!(!large.is_normal());
assert!(!large.is_finite());
}
let min_pos = ScalarF5E3::MIN_POS;
let tiny: ScalarF5E3 = min_pos / 1000.0;
if tiny.vanished() {
assert!(tiny.is_positive());
assert!(!tiny.is_normal());
assert!(!tiny.is_finite());
}
}
}