diff --git a/src/ExprNode.cc b/src/ExprNode.cc index cb84f912cb9f16881f9e0de3c2a81956aec93b70..48983d20c407baf4bf390c66060fb4d1be6973a1 100644 --- a/src/ExprNode.cc +++ b/src/ExprNode.cc @@ -5681,33 +5681,56 @@ BinaryOpNode::getPacAREC(int lhs_symb_id, int lhs_orig_symb_id, if (dynamic_cast<PacExpectationNode *>(it.first)) continue; - int pid, vid, lag; - double constant; + pair<int, vector<tuple<int, int, int, double>>> m; try { - tie(vid, lag, pid, constant) = it.first->matchVariableTimesConstantTimesParam(); - constant *= it.second; + m = {-1, {it.first->matchVariableTimesConstantTimesParam()}}; } catch (MatchFailureException &e) { - cerr << "Unsupported expression in PAC equation" << endl; - exit(EXIT_FAILURE); + try + { + m = it.first->matchParamTimesLinearCombinationOfVariables(); + } + catch (MatchFailureException &e) + { + cerr << "Unsupported expression in PAC equation" << endl; + exit(EXIT_FAILURE); + } } - int vidorig = datatree.symbol_table.getUltimateOrigSymbID(vid); - if (vidorig == lhs_symb_id || vidorig == lhs_orig_symb_id) + for (auto &t : m.second) + get<3>(t) *= it.second; // Update sign of constants + + int vid, lag, pidtmp, pid = get<0>(m); + double constant; + for (auto &t : m.second) { - // This is an autoregressive term - if (constant != 1 || pid == -1) + tie(vid, lag, pidtmp, constant) = t; + if (pid == -1) + pid = pidtmp; + else + if (pidtmp >= 0) + { + cerr << "unexpected parameter found in PAC equation" << endl; + exit(EXIT_FAILURE); + } + + int vidorig = datatree.symbol_table.getUltimateOrigSymbID(vid); + if (vidorig == lhs_symb_id || vidorig == lhs_orig_symb_id) { - cerr << "BinaryOpNode::getPacAREC: autoregressive terms must be of the form 'parameter*lagged_variable" << endl; - exit(EXIT_FAILURE); + // This is an autoregressive term + if (constant != 1 || pid == -1) + { + cerr << "BinaryOpNode::getPacAREC: autoregressive terms must be of the form 'parameter*lagged_variable" << endl; + exit(EXIT_FAILURE); + } + ar_params_and_vars.insert({pid, { vid, lag }}); } - ar_params_and_vars.insert({pid, { vid, lag }}); + else + // This is a residual additive term + additive_vars_params_and_constants.emplace_back(vid, lag, pid, constant); } - else - // This is a residual additive term - additive_vars_params_and_constants.emplace_back(vid, lag, pid, constant); } }