From 0f89569f7e59f065a8ec1ca414a2e9d26a43e649 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?S=C3=A9bastien=20Villemot?= Date: Tue, 16 Nov 2021 17:58:20 +0100 Subject: [PATCH] PAC: in the backward case, create an aux. var. for the pac_expectation expression MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit By the way, refactor the MCE case by merging two routines related to the Z₁ aux. var. This restores the symmetry with the backward case, now that the latter also has an aux. var. for the pac_expectation operator. Also store the aux. var. IDs in a structure common to the backward and MCE cases. --- src/DynamicModel.cc | 41 ++++++++++++++++++++++++++--------------- src/DynamicModel.hh | 21 ++++++++++----------- src/SubModel.cc | 22 ++++++++++------------ src/SubModel.hh | 11 ++++++++--- 4 files changed, 54 insertions(+), 41 deletions(-) diff --git a/src/DynamicModel.cc b/src/DynamicModel.cc index f6fd184e..1bc39dc1 100644 --- a/src/DynamicModel.cc +++ b/src/DynamicModel.cc @@ -3783,11 +3783,14 @@ DynamicModel::getPacTargetSymbId(const string &pac_model_name) const } void -DynamicModel::addPacModelConsistentExpectationEquation(const string &name, int discount_symb_id, - int pac_eq_max_lag, - ExprNode::subst_table_t &diff_subst_table, - map &pac_mce_z1_symb_ids, - map> &pac_mce_alpha_symb_ids) +DynamicModel::computePacModelConsistentExpectationSubstitution(const string &name, + int discount_symb_id, + int pac_eq_max_lag, + expr_t growth_correction_term, + ExprNode::subst_table_t &diff_subst_table, + map &pac_aux_var_symb_ids, + map> &pac_mce_alpha_symb_ids, + map &pac_expectation_substitution) { int pac_target_symb_id; try @@ -3813,7 +3816,7 @@ DynamicModel::addPacModelConsistentExpectationEquation(const string &name, int d cerr << "The variable/parameter '" << varname << "' conflicts with the variable that will be generated for the Z_1 variable of the '" << name << "' PAC model. Please rename it." << endl; exit(EXIT_FAILURE); } - pac_mce_z1_symb_ids[name] = mce_z1_symb_id; + pac_aux_var_symb_ids[name] = mce_z1_symb_id; expr_t A = One; expr_t fp = Zero; @@ -3913,18 +3916,11 @@ DynamicModel::addPacModelConsistentExpectationEquation(const string &name, int d neqs++; cout << "PAC Model Consistent Expectation: added " << neqs << " auxiliary variables and equations for model " << name << "." << endl; -} -void -DynamicModel::computePacModelConsistentExpectationSubstitution(const string &name, - expr_t growth_correction_term, - int pac_mce_z1_symb_id, - map &pac_expectation_substitution) -{ /* The growth correction term is not added to the definition of Z₁ because the latter is recursive. Rather put it at the level of the substition of pac_expectation operator. */ - pac_expectation_substitution[name] = AddPlus(AddVariable(pac_mce_z1_symb_id), growth_correction_term); + pac_expectation_substitution[name] = AddPlus(AddVariable(mce_z1_symb_id), growth_correction_term); } void @@ -3934,6 +3930,7 @@ DynamicModel::computePacBackwardExpectationSubstitution(const string &name, const string &aux_model_type, const vector &nonstationary, expr_t growth_correction_term, + map &pac_aux_var_symb_ids, map> &pac_h0_indices, map> &pac_h1_indices, map &pac_expectation_substitution) @@ -4001,7 +3998,21 @@ DynamicModel::computePacBackwardExpectationSubstitution(const string &name, } } - pac_expectation_substitution[name] = AddPlus(subExpr, growth_correction_term); + int expect_var_id; + string expect_var_name = "pac_expectation_" + name; + try + { + expect_var_id = symbol_table.addSymbol(expect_var_name, SymbolType::endogenous); + } + catch (SymbolTable::AlreadyDeclaredException &e) + { + cerr << "The variable/parameter '" << expect_var_name << "' conflicts with the variable that will be generated for the 'pac_expectation' expression of the '" << name << "' PAC model. Please rename it." << endl; + exit(EXIT_FAILURE); + } + addEquation(AddEqual(AddVariable(expect_var_id), AddPlus(subExpr, growth_correction_term)), -1); + + pac_aux_var_symb_ids[name] = expect_var_id; + pac_expectation_substitution[name] = AddVariable(expect_var_id); } void diff --git a/src/DynamicModel.hh b/src/DynamicModel.hh index 387f0e8b..80579ceb 100644 --- a/src/DynamicModel.hh +++ b/src/DynamicModel.hh @@ -528,20 +528,18 @@ public: //! Return target of the pac equation int getPacTargetSymbId(const string &pac_model_name) const; - /* For a PAC MCE model, add the variable and the equation defining Z₁. - The symbol IDs of the new endogenous and parameters are also added to - pac_mce_{z1,alpha}_symb_ids. */ - void addPacModelConsistentExpectationEquation(const string &name, int discount, - int pac_eq_max_lag, - ExprNode::subst_table_t &diff_subst_table, - map &pac_mce_z1_symb_ids, - map> &pac_mce_alpha_symb_ids); - /* For a PAC MCE model, fill pac_expectation_substitution with the - expression that will be substituted for the pac_expectation operator */ + expression that will be substituted for the pac_expectation operator. + In the process, add the variable and the equation defining Z₁. + The symbol IDs of the new endogenous are added to pac_aux_var_symb_ids, + and the new auxiliary parameters to pac_mce_alpha_symb_ids. + */ void computePacModelConsistentExpectationSubstitution(const string &name, + int discount_symb_id, int pac_eq_max_lag, expr_t growth_correction_term, - int pac_mce_z1_symb_id, + ExprNode::subst_table_t &diff_subst_table, + map &pac_aux_var_symb_ids, + map> &pac_mce_alpha_symb_ids, map &pac_expectation_substitution); @@ -554,6 +552,7 @@ public: const string &aux_model_type, const vector &nonstationary, expr_t growth_correction_term, + map &pac_aux_var_symb_ids, map> &pac_h0_indices, map> &pac_h1_indices, map &pac_expectation_substitution); diff --git a/src/SubModel.cc b/src/SubModel.cc index 3c911437..f484b2af 100644 --- a/src/SubModel.cc +++ b/src/SubModel.cc @@ -884,27 +884,25 @@ PacModelTable::transformPass(ExprNode::subst_table_t &diff_subst_table, } } - // In the MCE case, add the variable and the equation defining Z₁ - if (aux_model_name[name].empty()) - dynamic_model.addPacModelConsistentExpectationEquation(name, symbol_table.getID(discount[name]), - pacEquationMaxLag(name), - diff_subst_table, - mce_z1_symb_ids, mce_alpha_symb_ids); - // Compute the expressions that will be substituted for the pac_expectation operators expr_t growth_correction_term = dynamic_model.Zero; if (growth[name]) growth_correction_term = dynamic_model.AddTimes(growth[name], dynamic_model.AddVariable(growth_neutrality_params[name])); if (aux_model_name[name].empty()) dynamic_model.computePacModelConsistentExpectationSubstitution(name, + symbol_table.getID(discount[name]), + pacEquationMaxLag(name), growth_correction_term, - mce_z1_symb_ids[name], + diff_subst_table, + aux_var_symb_ids, + mce_alpha_symb_ids, pac_expectation_substitution); else dynamic_model.computePacBackwardExpectationSubstitution(name, lhs[name], max_lag, aux_model_type[name], nonstationary, growth_correction_term, + aux_var_symb_ids, h0_indices, h1_indices, pac_expectation_substitution); } @@ -986,10 +984,10 @@ PacModelTable::writeOutput(const string &basename, ostream &output) const output << "];" << endl; } - // Write PAC Model Consistent Expectation Z1 info - for (auto &[name, id] : mce_z1_symb_ids) - output << "M_.pac." << name << ".mce.z1 = " - << symbol_table.getTypeSpecificID(id) + 1 << ";" << endl; + // Write the auxiliary variable IDs created for the pac_expectation operator + for (auto &[name, id] : aux_var_symb_ids) + output << "M_.pac." << name << "." << (aux_model_name.at(name).empty() ? "mce.z1" : "aux_id") + << " = " << symbol_table.getTypeSpecificID(id) + 1 << ";" << endl; // Write PAC equation name info for (auto &[name, eq] : eq_name) diff --git a/src/SubModel.hh b/src/SubModel.hh index 00997796..ae84b685 100644 --- a/src/SubModel.hh +++ b/src/SubModel.hh @@ -205,12 +205,17 @@ private: pac_model_name → eq_name */ map eq_name; + /* Stores symb_ids for auxiliary endogenous created for the expression + substituted to the pac_expectation operator: + - in the backward case, this auxiliary contains exactly the + pac_expectation value + - in the MCE case, this auxiliary represents Z₁ (i.e. without the growth + correction term) + pac_model_name → symb_id */ + map aux_var_symb_ids; /* Stores symb_ids for alphas created by DynamicModel::addPacModelConsistentExpectationEquation() pac_model_name → mce_alpha_symb_ids */ map> mce_alpha_symb_ids; - /* Stores symb_ids for z1s created by DynamicModel::addPacModelConsistentExpectationEquation() - pac_model_name → mce_z1_symb_id */ - map mce_z1_symb_ids; /* Stores symb_ids for h0, h1 parameters pac_model_name → parameter symb_ids */ map> h0_indices, h1_indices;