use symplex::expr;
use symplex::prelude::*;
#[test]
fn stripper_collector_pythagorean_plus_constant() {
let ctx = Context::new();
symplex::syms!(ctx; x);
let expr = expr!(ctx, sin(x) ^ 2 + cos(x) ^ 2 + 5);
let result = expr.simplify();
assert_eq!(format!("{result}"), "6");
}
#[test]
fn stripper_collector_pythagorean_in_large_sum() {
let ctx = Context::new();
symplex::syms!(ctx; x, a, b, c);
let expr = &a + &b + &x.sin().powi(2) + &x.cos().powi(2) + &c;
let result = expr.simplify();
let s = format!("{result}");
assert!(!s.contains("sin"), "should not contain sin: {s}");
assert!(!s.contains("cos"), "should not contain cos: {s}");
}
#[test]
fn stripper_collector_5_term_add() {
let ctx = Context::new();
symplex::syms!(ctx; x);
let expr = expr!(ctx, 1 + 2 + sin(x) ^ 2 + 3 + cos(x) ^ 2);
let result = expr.simplify();
assert_eq!(format!("{result}"), "7");
}
#[test]
fn stripper_collector_6_term_two_symbols() {
let ctx = Context::new();
symplex::syms!(ctx; x, y, z);
let expr = &y + &z + &x.sin().powi(2) + 10 + &x.cos().powi(2) + &y;
let result = expr.simplify();
let s = format!("{result}");
assert!(!s.contains("sin"), "sin should have been eliminated: {s}");
assert!(!s.contains("cos"), "cos should have been eliminated: {s}");
assert!(s.contains("11"), "constant part should be 11: {s}");
}
#[test]
fn stripper_collector_cosh_sinh_in_sum() {
let ctx = Context::new();
symplex::syms!(ctx; x);
let expr = expr!(ctx, cosh(x) ^ 2 - sinh(x) ^ 2 + 3);
let result = expr.simplify();
assert_eq!(format!("{result}"), "4");
}
#[test]
fn stripper_collector_exp_mul_in_product() {
let ctx = Context::new();
symplex::syms!(ctx; a, b, z);
let expr = &z * &a.exp() * &b.exp();
let result = expr.simplify();
let s = format!("{result}");
assert!(s.contains("exp("), "should still contain exp: {s}");
assert!(s.contains("z"), "should still contain z: {s}");
let exp_count = s.matches("exp(").count();
assert_eq!(
exp_count, 1,
"should have exactly one exp after combining: {s}"
);
}
#[test]
fn regression_exact_2_term_pythagorean() {
let ctx = Context::new();
symplex::syms!(ctx; x);
let expr = expr!(ctx, sin(x) ^ 2 + cos(x) ^ 2);
let result = expr.simplify();
assert_eq!(format!("{result}"), "1");
}
#[test]
fn regression_3_term_add_pythagorean() {
let ctx = Context::new();
symplex::syms!(ctx; x);
let expr = expr!(ctx, sin(x) ^ 2 + cos(x) ^ 2 + 3);
let result = expr.simplify();
assert_eq!(format!("{result}"), "4");
}
#[test]
fn no_false_match_different_args() {
let ctx = Context::new();
symplex::syms!(ctx; x, y);
let expr = expr!(ctx, sin(x) ^ 2 + cos(y) ^ 2 + 3);
let result = expr.simplify();
let s = format!("{result}");
assert!(s.contains("sin"), "sin should remain (different args): {s}");
assert!(s.contains("cos"), "cos should remain (different args): {s}");
}
#[test]
fn no_false_match_sin_sin() {
let ctx = Context::new();
symplex::syms!(ctx; x);
let expr = expr!(ctx, sin(x) ^ 2 + sin(x) ^ 2);
let result = expr.simplify();
let s = format!("{result}");
assert!(s.contains("sin"), "should still contain sin: {s}");
assert_ne!(s, "1", "should not reduce to 1");
}