diff --git a/src/ModelTree.cc b/src/ModelTree.cc index ef94feaabb12ee9496c83241b3c7f1ad7df33d7b..b8fb83fd7e4f9ba6b7be8d8cac5e22d1623be6d4 100644 --- a/src/ModelTree.cc +++ b/src/ModelTree.cc @@ -331,9 +331,8 @@ ModelTree::computeNonSingularNormalization(const jacob_map_t &contemporaneous_ja { cout << "Normalization failed with cutoff, trying symbolic normalization..." << endl; /* If no non-singular normalization can be found, try to find a - normalization even with a potential singularity. - TODO: Explain why symbolic_jacobian is not contemporaneous. */ - auto symbolic_jacobian = computeSymbolicJacobian(); + normalization even with a potential singularity. */ + auto symbolic_jacobian = computeSymbolicJacobian(true); found_normalization = computeNormalization(symbolic_jacobian, true); } @@ -661,7 +660,7 @@ ModelTree::computeBlockDecomposition(int prologue, int epilogue) For detecting dependencies between variables, use the symbolic adjacency matrix */ VariableDependencyGraph G(nb_simvars); - for (const auto &[key, value] : computeSymbolicJacobian()) + for (const auto &[key, value] : computeSymbolicJacobian(false)) { auto [eq, endo] = key; if (eq_idx_orig2block[eq] >= prologue @@ -1878,7 +1877,7 @@ ModelTree::collectFirstOrderDerivativesEndogenous() } ModelTree::jacob_map_t -ModelTree::computeSymbolicJacobian() const +ModelTree::computeSymbolicJacobian(bool contemporaneous_only) const { jacob_map_t symbolic_jacobian; for (int i = 0; i < static_cast<int>(equations.size()); i++) @@ -1886,7 +1885,8 @@ ModelTree::computeSymbolicJacobian() const set<pair<int, int>> endos_and_lags; equations[i]->collectEndogenous(endos_and_lags); for (const auto &[endo, lag] : endos_and_lags) - symbolic_jacobian[{ i, endo }] = 1; + if (!contemporaneous_only || lag == 0) + symbolic_jacobian[{ i, endo }] = 1; } return symbolic_jacobian; } diff --git a/src/ModelTree.hh b/src/ModelTree.hh index 8b08051338b761e0c7354a511823f72b1abe0d3f..c6312782224264f8f4ac455d0732da0895f82495 100644 --- a/src/ModelTree.hh +++ b/src/ModelTree.hh @@ -424,8 +424,10 @@ private: static set<filesystem::path> mex_compilation_done; /* Compute a pseudo-Jacobian whose all elements are either zero or one, - depending on whether the variable symbolically appears in the equation */ - jacob_map_t computeSymbolicJacobian() const; + depending on whether the variable symbolically appears in the equation. If + contemporaneous_only=true, only considers contemporaneous occurences of + variables; otherwise also considers leads and lags. */ + jacob_map_t computeSymbolicJacobian(bool contemporaneous_only) const; // Compute {var,eq}_idx_orig2block from {var,eq}_idx_block2orig void updateReverseVariableEquationOrderings();