diff --git a/core/src/superpose.cc b/core/src/superpose.cc index 1d4fad622161e538c51eabf688360c73eb1381d6..7eb504029aace3c2305ae4a438afccbcf0e1e55a 100644 --- a/core/src/superpose.cc +++ b/core/src/superpose.cc @@ -547,7 +547,9 @@ void RigidBlocks(EMatX3& pos_one, EMatX3& pos_two, distance_thresh, current_indices, false); - unique_blocks[current_indices] = t;; + // only add if iterative superposition converged => number of indices + // must be larger than 3 + if(current_indices.size() >= 3) unique_blocks[current_indices] = t; } for(std::map<std::vector<uint>, geom::Mat4>::iterator i = unique_blocks.begin(); diff --git a/core/src/superpose.hh b/core/src/superpose.hh index 36b5a4b533e87f411a1ded7b46cc6844563f5b7d..d9a558da2d51e3e57422e9a6b4ea4428b56077c0 100644 --- a/core/src/superpose.hh +++ b/core/src/superpose.hh @@ -46,35 +46,38 @@ std::pair<geom::Mat4,Real> Superposition(EMatX3& pos_one, EMatX3& pos_two, void FillRMSDMatrix(EMatX3List& position_list, Real** data); // ITERATIVE MIN RMSD SUPERPOSITION ALGORITHMS +// You'll always know what indices are actually used for the final +// superposition. If there are less than 3, you can expect, that the +// algorithm didn't converge. // Get minimal possible RMSD between points defined in pos_one and pos_two Real SuperposedRMSD(EMatX3& pos_one, EMatX3& pos_two, - uint max_iterations, - Real distance_thresh, - std::vector<uint>& indices, - bool apply_superposition = false); + uint max_iterations, + Real distance_thresh, + std::vector<uint>& indices, + bool apply_superposition = false); // Get transformation to superpose points in pos_one onto the ones in pos_two geom::Mat4 MinRMSDSuperposition(EMatX3& pos_one, EMatX3& pos_two, - uint max_iterations, - Real distance_thresh, - std::vector<uint>& indices, - bool apply_superposition = false); + uint max_iterations, + Real distance_thresh, + std::vector<uint>& indices, + bool apply_superposition = false); // Get both things... std::pair<geom::Mat4,Real> Superposition(EMatX3& pos_one, EMatX3& pos_two, - uint max_iterations, - Real distance_thresh, - std::vector<uint>& indices, - bool apply_superposition = false); + uint max_iterations, + Real distance_thresh, + std::vector<uint>& indices, + bool apply_superposition = false); void RigidBlocks(EMatX3& pos_one, EMatX3& pos_two, uint window_length, - uint max_iterations, - Real distance_thresh, - std::vector<std::vector<uint> >& indices, - std::vector<geom::Mat4>& transformations); + uint max_iterations, + Real distance_thresh, + std::vector<std::vector<uint> >& indices, + std::vector<geom::Mat4>& transformations); // Fill row of given Eigen Matrix with 3 entries of Vec3 diff --git a/loop/src/backbone.cc b/loop/src/backbone.cc index 8376a87cc960e14e826ce85fe25fc63e74e8c394..0a04aa1260134c0c718f9b05387d298886f9b754 100644 --- a/loop/src/backbone.cc +++ b/loop/src/backbone.cc @@ -1131,11 +1131,17 @@ geom::Mat4 BackboneList::GetTransformIterative(const BackboneList& other, BackboneList::ExtractEigenNCACPos(other, pos_two); } - std::vector<uint> empty_index_vec; - return core::MinRMSDSuperposition(pos_one, pos_two, max_iterations, - distance_thresh, empty_index_vec, false); + std::vector<uint> index_vec; + geom::Mat4 t = core::MinRMSDSuperposition(pos_one, pos_two, max_iterations, + distance_thresh, index_vec, false); + if(index_vec.size() >= 3) { + return t; + } else { + // iterative superposition did not converge, let's use normal superposition + // as fallback + return core::MinRMSDSuperposition(pos_one, pos_two); + } } - /////////////////////////////////////////////////////////////////////////////// // BackboneList private void BackboneList::ConstructBackboneList_(const String& sequence,