From c5fc2e38c1361aef5820f91a4b1d0375e97f3af9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?S=C3=A9bastien=20Villemot?= Date: Mon, 28 Jan 2019 15:15:58 +0100 Subject: [PATCH] Simplify log(1/x) into -log(x) (and similarly for log10) --- src/DataTree.cc | 28 ++++++++++++++++++++-------- 1 file changed, 20 insertions(+), 8 deletions(-) diff --git a/src/DataTree.cc b/src/DataTree.cc index 0e3c22b7..7a60c67d 100644 --- a/src/DataTree.cc +++ b/src/DataTree.cc @@ -357,29 +357,41 @@ DataTree::AddExp(expr_t iArg1) expr_t DataTree::AddLog(expr_t iArg1) { - if (iArg1 != Zero && iArg1 != One) - return AddUnaryOp(UnaryOpcode::log, iArg1); - else if (iArg1 == One) + if (iArg1 == One) return Zero; - else + + if (iArg1 == Zero) { cerr << "ERROR: log(0) not defined!" << endl; exit(EXIT_FAILURE); } + + // Try to simplify log(1/x) into -log(x) + auto barg1 = dynamic_cast(iArg1); + if (barg1 && barg1->op_code == BinaryOpcode::divide && barg1->arg1 == One) + return AddUMinus(AddLog(barg1->arg2)); + + return AddUnaryOp(UnaryOpcode::log, iArg1); } expr_t DataTree::AddLog10(expr_t iArg1) { - if (iArg1 != Zero && iArg1 != One) - return AddUnaryOp(UnaryOpcode::log10, iArg1); - else if (iArg1 == One) + if (iArg1 == One) return Zero; - else + + if (iArg1 == Zero) { cerr << "ERROR: log10(0) not defined!" << endl; exit(EXIT_FAILURE); } + + // Try to simplify log10(1/x) into -log10(x) + auto barg1 = dynamic_cast(iArg1); + if (barg1 && barg1->op_code == BinaryOpcode::divide && barg1->arg1 == One) + return AddUMinus(AddLog10(barg1->arg2)); + + return AddUnaryOp(UnaryOpcode::log10, iArg1); } expr_t