use tensorlogic_ir::TLExpr;
use super::pe_arith::try_pe_arith;
use super::pe_logic::try_pe_logic;
use super::pe_math::try_pe_math;
use super::pe_passthrough::try_pe_passthrough;
use super::pe_quantifiers::try_pe_quantifiers;
use super::types::{PEConfig, PEEnv, PEStats};
pub(super) fn pe_rec(
expr: TLExpr,
env: &PEEnv,
config: &PEConfig,
depth: usize,
stats: &mut PEStats,
) -> TLExpr {
stats.nodes_visited = stats.nodes_visited.saturating_add(1);
if depth > config.max_depth {
return expr;
}
if let TLExpr::Constant(_) = &expr {
return expr;
}
if let TLExpr::Pred { name, args } = &expr {
if args.is_empty() {
if let Some(pval) = env.lookup(name) {
stats.nodes_reduced = stats.nodes_reduced.saturating_add(1);
return pval.to_expr();
}
}
return expr;
}
let expr = match try_pe_arith(expr, env, config, depth, stats) {
Ok(r) => return r,
Err(e) => e,
};
let expr = match try_pe_math(expr, env, config, depth, stats) {
Ok(r) => return r,
Err(e) => e,
};
let expr = match try_pe_logic(expr, env, config, depth, stats) {
Ok(r) => return r,
Err(e) => e,
};
let expr = match try_pe_quantifiers(expr, env, config, depth, stats) {
Ok(r) => return r,
Err(e) => e,
};
let expr = match try_pe_passthrough(expr, env, config, depth, stats) {
Ok(r) => return r,
Err(e) => e,
};
expr
}