From bfd93f4ac0ff1eeece0883faba993052b9d2ea57 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?St=C3=A9phane=20Adjemia=20=28Scylla=29?= <stepan@dynare.org> Date: Thu, 25 Oct 2018 10:08:21 +0200 Subject: [PATCH] Fixed estimated_params_init behaviour... ... when an initial value is given to a parameter that is not estimated. The generated driver file was crashing with cryptic error message because we were searching in the first (and second) column of a potentially empty array with 0 columns. The fix is to initialize the fields of estimated_params_ with empty arrays with 10 columns (ie zeros(0, 10)). Also print a message in the matlab command window if parameter declared in estimated_params_init is not estimated. --- src/ComputingTasks.cc | 51 ++++++++++++++++++++++++++++++++++--------- 1 file changed, 41 insertions(+), 10 deletions(-) diff --git a/src/ComputingTasks.cc b/src/ComputingTasks.cc index 2f256a86..9c87b5eb 100644 --- a/src/ComputingTasks.cc +++ b/src/ComputingTasks.cc @@ -1391,11 +1391,11 @@ EstimatedParamsStatement::checkPass(ModFileStructure &mod_file_struct, WarningCo void EstimatedParamsStatement::writeOutput(ostream &output, const string &basename, bool minimal_workspace) const { - output << "estim_params_.var_exo = [];" << endl - << "estim_params_.var_endo = [];" << endl - << "estim_params_.corrx = [];" << endl - << "estim_params_.corrn = [];" << endl - << "estim_params_.param_vals = [];" << endl; + output << "estim_params_.var_exo = zeros(0, 10);" << endl + << "estim_params_.var_endo = zeros(0, 10);" << endl + << "estim_params_.corrx = zeros(0, 10);" << endl + << "estim_params_.corrn = zeros(0, 10);" << endl + << "estim_params_.param_vals = zeros(0, 10);" << endl; for (const auto & it : estim_params_list) { @@ -1514,6 +1514,8 @@ EstimatedParamsInitStatement::writeOutput(ostream &output, const string &basenam if (use_calibration) output << "options_.use_calibration_initialization = 1;" << endl; + bool skipline = false; + for (const auto & it : estim_params_list) { int symb_id = symbol_table.getTypeSpecificID(it.name) + 1; @@ -1524,23 +1526,38 @@ EstimatedParamsInitStatement::writeOutput(ostream &output, const string &basenam if (symb_type == SymbolType::exogenous) { output << "tmp1 = find(estim_params_.var_exo(:,1)==" << symb_id << ");" << endl; - output << "estim_params_.var_exo(tmp1,2) = "; + output << "if isempty(tmp1)" << endl; + output << " disp(sprintf('The standard deviation of %s is not estimated (the value provided in estimated_params_init is not used).', M_.exo_names{" << symb_id << "}))" << endl; + skipline = true; + output << "else" << endl; + output << " estim_params_.var_exo(tmp1,2) = "; it.init_val->writeOutput(output); output << ";" << endl; + output << "end" << endl; } else if (symb_type == SymbolType::endogenous) { output << "tmp1 = find(estim_params_.var_endo(:,1)==" << symb_id << ");" << endl; - output << "estim_params_.var_endo(tmp1,2) = "; + output << "if isempty(tmp1)" << endl; + output << " disp(sprintf('The standard deviation of the measurement error on %s is not estimated (the value provided in estimated_params_init is not used).', M_.endo_names{" << symb_id << "}))" << endl; + skipline = true; + output << "else" << endl; + output << " estim_params_.var_endo(tmp1,2) = "; it.init_val->writeOutput(output); output << ";" << endl; + output << "end" << endl; } else if (symb_type == SymbolType::parameter) { output << "tmp1 = find(estim_params_.param_vals(:,1)==" << symb_id << ");" << endl; - output << "estim_params_.param_vals(tmp1,2) = "; + output << "if isempty(tmp1)" << endl; + output << " disp(sprintf('Parameter %s is not estimated (the value provided in estimated_params_init is not used).', M_.param_names{" << symb_id << "}))" << endl; + skipline = true; + output << "else" << endl; + output << " estim_params_.param_vals(tmp1,2) = "; it.init_val->writeOutput(output); output << ";" << endl; + output << "end" << endl; } } else @@ -1549,20 +1566,34 @@ EstimatedParamsInitStatement::writeOutput(ostream &output, const string &basenam { output << "tmp1 = find((estim_params_.corrx(:,1)==" << symb_id << " & estim_params_.corrx(:,2)==" << symbol_table.getTypeSpecificID(it.name2)+1 << ") | " << "(estim_params_.corrx(:,2)==" << symb_id << " & estim_params_.corrx(:,1)==" << symbol_table.getTypeSpecificID(it.name2)+1 << "));" << endl; - output << "estim_params_.corrx(tmp1,3) = "; + output << "if isempty(tmp1)" << endl; + output << " disp(sprintf('The correlation between %s and %s is not estimated (the value provided in estimated_params_init is not used).', M_.exo_names{" + << symb_id << "}, M_.exo_names{" << symbol_table.getTypeSpecificID(it.name2)+1 << "}))" << endl; + skipline = true; + output << "else" << endl; + output << " estim_params_.corrx(tmp1,3) = "; it.init_val->writeOutput(output); output << ";" << endl; + output << "end" << endl; } else if (symb_type == SymbolType::endogenous) { output << "tmp1 = find((estim_params_.corrn(:,1)==" << symb_id << " & estim_params_.corrn(:,2)==" << symbol_table.getTypeSpecificID(it.name2)+1 << ") | " << "(estim_params_.corrn(:,2)==" << symb_id << " & estim_params_.corrn(:,1)==" << symbol_table.getTypeSpecificID(it.name2)+1 << "));" << endl; - output << "estim_params_.corrn(tmp1,3) = "; + output << "if isempty(tmp1)" << endl; + output << " disp(sprintf('The correlation between measurement errors on %s and %s is not estimated (the value provided in estimated_params_init is not used).', M_.endo_names{" + << symb_id << "}, M_.endo_names{" << symbol_table.getTypeSpecificID(it.name2)+1 << "}))" << endl; + skipline = true; + output << "else" << endl; + output << " estim_params_.corrn(tmp1,3) = "; it.init_val->writeOutput(output); output << ";" << endl; + output << "end" << endl; } } } + if (skipline == true) + output << "skipline()" << endl; } void -- GitLab