Rosetta 3.5
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
rms_util.tmpl.hh
Go to the documentation of this file.
1 // :noTabs=false:tabSize=4:indentSize=4:
2 //
3 // (c) Copyright Rosetta Commons Member Institutions.
4 // (c) This file is part of the Rosetta software suite and is made available under license.
5 // (c) The Rosetta software is developed by the contributing members of the Rosetta Commons.
6 // (c) For more information, see http://www.rosettacommons.org. Questions about this can be
7 // (c) addressed to University of Washington UW TechTransfer, email: license@u.washington.edu.
8 
9 /// @file core/rms/rms_util.tmpl.hh
10 /// @brief RMS stuff from rosetta++ that requires templates
11 /// @author James Thompson
12 /// @author Ian Davis
13 /// @date Wed Aug 22 12:10:37 2007
14 
15 #ifndef INCLUDED_core_scoring_rms_util_tmpl_HH
16 #define INCLUDED_core_scoring_rms_util_tmpl_HH
17 
18 #include <core/types.hh>
19 #include <core/pose/Pose.hh>
21 #include <core/scoring/rms_util.hh>
22 
23 #include <numeric/model_quality/rms.hh>
24 // AUTO-REMOVED #include <numeric/model_quality/maxsub.hh>
25 #include <numeric/xyzVector.hh>
26 
27 #include <ObjexxFCL/FArray1D.hh>
28 #include <ObjexxFCL/FArray2D.hh>
29 #include <ObjexxFCL/FArray1A.hh>
30 #include <ObjexxFCL/FArray2A.hh>
31 #include <list>
32 
33 //Auto Headers
34 #include <platform/types.hh>
35 #include <core/chemical/AA.hh>
37 #include <core/chemical/Adduct.hh>
54 #include <core/chemical/types.hh>
85 #include <core/id/AtomID.fwd.hh>
86 #include <core/id/AtomID.hh>
88 #include <core/id/AtomID_Map.hh>
90 #include <core/id/DOF_ID.fwd.hh>
91 #include <core/id/DOF_ID.hh>
95 #include <core/id/NamedAtomID.hh>
98 #include <core/id/TorsionID.fwd.hh>
99 #include <core/id/types.hh>
106 #include <core/kinematics/Edge.hh>
110 #include <core/kinematics/Jump.hh>
112 #include <core/kinematics/RT.fwd.hh>
113 #include <core/kinematics/RT.hh>
116 #include <core/kinematics/Stub.hh>
119 #include <core/pose/PDBInfo.fwd.hh>
120 #include <core/pose/Pose.fwd.hh>
131 #include <utility/Bound.fwd.hh>
132 #include <utility/Bound.hh>
133 #include <utility/assert.hh>
134 #include <utility/down_cast.hh>
135 #include <utility/exit.hh>
136 #include <utility/stream_util.hh>
137 #include <utility/string_util.hh>
138 #include <utility/vector0_bool.hh>
139 #include <utility/vector1.fwd.hh>
140 #include <utility/vector1.hh>
141 #include <utility/vector1_bool.hh>
142 #include <utility/vectorL.fwd.hh>
143 #include <utility/vectorL.hh>
144 #include <utility/vectorL_Selector.hh>
145 #include <utility/vectorL_bool.hh>
146 #include <utility/file/FileName.fwd.hh>
147 #include <utility/file/FileName.hh>
148 #include <utility/file/PathName.fwd.hh>
149 #include <utility/file/PathName.hh>
150 #include <utility/keys/AutoKey.fwd.hh>
151 #include <utility/keys/AutoKey.hh>
152 #include <utility/keys/Key.fwd.hh>
153 #include <utility/keys/Key.hh>
154 #include <utility/keys/Key2Tuple.fwd.hh>
155 #include <utility/keys/Key2Tuple.hh>
156 #include <utility/keys/Key3Tuple.fwd.hh>
157 #include <utility/keys/Key3Tuple.hh>
158 #include <utility/keys/Key4Tuple.fwd.hh>
159 #include <utility/keys/Key4Tuple.hh>
160 #include <utility/keys/KeyLess.fwd.hh>
161 #include <utility/keys/KeyLookup.fwd.hh>
162 #include <utility/keys/KeyLookup.hh>
163 #include <utility/keys/NoClient.fwd.hh>
164 #include <utility/keys/NoClient.hh>
165 #include <utility/keys/SmallKeyVector.fwd.hh>
166 #include <utility/keys/SmallKeyVector.hh>
167 #include <utility/keys/UserKey.fwd.hh>
168 #include <utility/keys/VariantKey.fwd.hh>
169 #include <utility/keys/VariantKey.hh>
170 #include <utility/options/AnyOption.fwd.hh>
171 #include <utility/options/AnyOption.hh>
172 #include <utility/options/AnyVectorOption.fwd.hh>
173 #include <utility/options/AnyVectorOption.hh>
174 #include <utility/options/BooleanOption.fwd.hh>
175 #include <utility/options/BooleanOption.hh>
176 #include <utility/options/BooleanVectorOption.fwd.hh>
177 #include <utility/options/BooleanVectorOption.hh>
178 #include <utility/options/FileOption.fwd.hh>
179 #include <utility/options/FileOption.hh>
180 #include <utility/options/FileVectorOption.fwd.hh>
181 #include <utility/options/FileVectorOption.hh>
182 #include <utility/options/IntegerOption.fwd.hh>
183 #include <utility/options/IntegerOption.hh>
184 #include <utility/options/IntegerVectorOption.fwd.hh>
185 #include <utility/options/IntegerVectorOption.hh>
186 #include <utility/options/Option.fwd.hh>
187 #include <utility/options/Option.hh>
188 #include <utility/options/OptionCollection.fwd.hh>
189 #include <utility/options/OptionCollection.hh>
190 #include <utility/options/PathOption.fwd.hh>
191 #include <utility/options/PathOption.hh>
192 #include <utility/options/PathVectorOption.fwd.hh>
193 #include <utility/options/PathVectorOption.hh>
194 #include <utility/options/RealOption.fwd.hh>
195 #include <utility/options/RealOption.hh>
196 #include <utility/options/RealVectorOption.fwd.hh>
197 #include <utility/options/RealVectorOption.hh>
198 #include <utility/options/ScalarOption.fwd.hh>
199 #include <utility/options/ScalarOption.hh>
200 #include <utility/options/ScalarOption_T_.fwd.hh>
201 #include <utility/options/ScalarOption_T_.hh>
202 #include <utility/options/StringOption.fwd.hh>
203 #include <utility/options/StringOption.hh>
204 #include <utility/options/StringVectorOption.fwd.hh>
205 #include <utility/options/StringVectorOption.hh>
206 #include <utility/options/VariantOption.fwd.hh>
207 #include <utility/options/VariantOption.hh>
208 #include <utility/options/VectorOption.fwd.hh>
209 #include <utility/options/VectorOption.hh>
210 #include <utility/options/VectorOption_T_.fwd.hh>
211 #include <utility/options/VectorOption_T_.hh>
212 #include <utility/options/mpi_stderr.hh>
213 #include <utility/options/keys/AnyOptionKey.fwd.hh>
214 #include <utility/options/keys/AnyOptionKey.hh>
215 #include <utility/options/keys/AnyVectorOptionKey.fwd.hh>
216 #include <utility/options/keys/AnyVectorOptionKey.hh>
217 #include <utility/options/keys/BooleanOptionKey.fwd.hh>
218 #include <utility/options/keys/BooleanOptionKey.hh>
219 #include <utility/options/keys/BooleanVectorOptionKey.fwd.hh>
220 #include <utility/options/keys/BooleanVectorOptionKey.hh>
221 #include <utility/options/keys/FileOptionKey.fwd.hh>
222 #include <utility/options/keys/FileOptionKey.hh>
223 #include <utility/options/keys/FileVectorOptionKey.fwd.hh>
224 #include <utility/options/keys/FileVectorOptionKey.hh>
225 #include <utility/options/keys/IntegerOptionKey.fwd.hh>
226 #include <utility/options/keys/IntegerOptionKey.hh>
227 #include <utility/options/keys/IntegerVectorOptionKey.fwd.hh>
228 #include <utility/options/keys/IntegerVectorOptionKey.hh>
229 #include <utility/options/keys/OptionKey.fwd.hh>
230 #include <utility/options/keys/OptionKey.hh>
231 #include <utility/options/keys/OptionKeys.hh>
232 #include <utility/options/keys/PathOptionKey.fwd.hh>
233 #include <utility/options/keys/PathOptionKey.hh>
234 #include <utility/options/keys/PathVectorOptionKey.fwd.hh>
235 #include <utility/options/keys/PathVectorOptionKey.hh>
236 #include <utility/options/keys/RealOptionKey.fwd.hh>
237 #include <utility/options/keys/RealOptionKey.hh>
238 #include <utility/options/keys/RealVectorOptionKey.fwd.hh>
239 #include <utility/options/keys/RealVectorOptionKey.hh>
240 #include <utility/options/keys/ScalarOptionKey.fwd.hh>
241 #include <utility/options/keys/ScalarOptionKey.hh>
242 #include <utility/options/keys/StringOptionKey.fwd.hh>
243 #include <utility/options/keys/StringOptionKey.hh>
244 #include <utility/options/keys/StringVectorOptionKey.fwd.hh>
245 #include <utility/options/keys/StringVectorOptionKey.hh>
246 #include <utility/options/keys/VectorOptionKey.fwd.hh>
247 #include <utility/options/keys/VectorOptionKey.hh>
248 #include <utility/options/keys/all.hh>
249 #include <utility/pointer/ReferenceCount.fwd.hh>
250 #include <utility/pointer/ReferenceCount.hh>
251 #include <utility/pointer/access_ptr.fwd.hh>
252 #include <utility/pointer/access_ptr.hh>
253 #include <utility/pointer/owning_ptr.functions.hh>
254 #include <utility/pointer/owning_ptr.fwd.hh>
255 #include <utility/pointer/owning_ptr.hh>
256 #include <utility/signals/BufferedSignalHub.fwd.hh>
257 #include <utility/signals/BufferedSignalHub.hh>
258 #include <utility/signals/Link.fwd.hh>
259 #include <utility/signals/Link.hh>
260 #include <utility/signals/LinkUnit.fwd.hh>
261 #include <utility/signals/LinkUnit.hh>
262 #include <utility/signals/PausableSignalHub.fwd.hh>
263 #include <utility/signals/PausableSignalHub.hh>
264 #include <utility/signals/SignalHub.fwd.hh>
265 #include <utility/signals/SignalHub.hh>
266 #include <numeric/HomogeneousTransform.hh>
267 #include <numeric/NumericTraits.hh>
268 #include <numeric/constants.hh>
269 #include <numeric/conversions.hh>
270 #include <numeric/numeric.functions.hh>
271 #include <numeric/sphericalVector.fwd.hh>
272 #include <numeric/sphericalVector.hh>
273 #include <numeric/trig.functions.hh>
274 #include <numeric/types.hh>
275 #include <numeric/xyz.functions.fwd.hh>
276 #include <numeric/xyz.functions.hh>
277 #include <numeric/xyzMatrix.fwd.hh>
278 #include <numeric/xyzMatrix.hh>
279 #include <numeric/xyzVector.fwd.hh>
280 #include <numeric/internal/ColPointers.hh>
281 #include <numeric/internal/ColVectors.hh>
282 #include <numeric/internal/ColsPointer.hh>
283 #include <numeric/internal/RowPointers.hh>
284 #include <numeric/internal/RowVectors.hh>
285 #include <numeric/internal/RowsPointer.hh>
286 #include <ObjexxFCL/Dimension.fwd.hh>
287 #include <ObjexxFCL/Dimension.hh>
288 #include <ObjexxFCL/DimensionExpression.hh>
289 #include <ObjexxFCL/DynamicIndexRange.fwd.hh>
290 #include <ObjexxFCL/DynamicIndexRange.hh>
291 #include <ObjexxFCL/FArray.all.fwd.hh>
292 #include <ObjexxFCL/FArray.fwd.hh>
293 #include <ObjexxFCL/FArray.hh>
294 #include <ObjexxFCL/FArray1.all.fwd.hh>
295 #include <ObjexxFCL/FArray1.fwd.hh>
296 #include <ObjexxFCL/FArray1.hh>
297 #include <ObjexxFCL/FArray1A.fwd.hh>
298 #include <ObjexxFCL/FArray1D.fwd.hh>
299 #include <ObjexxFCL/FArray1P.fwd.hh>
300 #include <ObjexxFCL/FArray1P.hh>
301 #include <ObjexxFCL/FArray2.all.fwd.hh>
302 #include <ObjexxFCL/FArray2.fwd.hh>
303 #include <ObjexxFCL/FArray2.hh>
304 #include <ObjexxFCL/FArray2A.fwd.hh>
305 #include <ObjexxFCL/FArray2D.fwd.hh>
306 #include <ObjexxFCL/FArray2P.fwd.hh>
307 #include <ObjexxFCL/FArray2P.hh>
308 #include <ObjexxFCL/FArray3.all.fwd.hh>
309 #include <ObjexxFCL/FArray3.fwd.hh>
310 #include <ObjexxFCL/FArray3A.fwd.hh>
311 #include <ObjexxFCL/FArray3D.fwd.hh>
312 #include <ObjexxFCL/FArray3P.fwd.hh>
313 #include <ObjexxFCL/FArray4.all.fwd.hh>
314 #include <ObjexxFCL/FArray4.fwd.hh>
315 #include <ObjexxFCL/FArray4A.fwd.hh>
316 #include <ObjexxFCL/FArray4D.fwd.hh>
317 #include <ObjexxFCL/FArray4P.fwd.hh>
318 #include <ObjexxFCL/FArray5.all.fwd.hh>
319 #include <ObjexxFCL/FArray5.fwd.hh>
320 #include <ObjexxFCL/FArray5A.fwd.hh>
321 #include <ObjexxFCL/FArray5D.fwd.hh>
322 #include <ObjexxFCL/FArray5P.fwd.hh>
323 #include <ObjexxFCL/FArray6.all.fwd.hh>
324 #include <ObjexxFCL/FArray6.fwd.hh>
325 #include <ObjexxFCL/FArray6A.fwd.hh>
326 #include <ObjexxFCL/FArray6D.fwd.hh>
327 #include <ObjexxFCL/FArray6P.fwd.hh>
328 #include <ObjexxFCL/FArrayInitializer.fwd.hh>
329 #include <ObjexxFCL/FArrayInitializer.hh>
330 #include <ObjexxFCL/FArraySection.fwd.hh>
331 #include <ObjexxFCL/FArraySection.hh>
332 #include <ObjexxFCL/FArrayTraits.fwd.hh>
333 #include <ObjexxFCL/FArrayTraits.hh>
334 #include <ObjexxFCL/IndexRange.fwd.hh>
335 #include <ObjexxFCL/IndexRange.hh>
336 #include <ObjexxFCL/InitializerSentinel.hh>
337 #include <ObjexxFCL/KeyFArray1D.fwd.hh>
338 #include <ObjexxFCL/KeyFArray2D.fwd.hh>
339 #include <ObjexxFCL/KeyFArray3D.fwd.hh>
340 #include <ObjexxFCL/KeyFArray4D.fwd.hh>
341 #include <ObjexxFCL/KeyFArray5D.fwd.hh>
342 #include <ObjexxFCL/KeyFArray6D.fwd.hh>
343 #include <ObjexxFCL/Observer.fwd.hh>
344 #include <ObjexxFCL/Observer.hh>
345 #include <ObjexxFCL/ObserverMulti.hh>
346 #include <ObjexxFCL/ObserverSingle.hh>
347 #include <ObjexxFCL/ProxySentinel.hh>
348 #include <ObjexxFCL/SetWrapper.fwd.hh>
349 #include <ObjexxFCL/Star.fwd.hh>
350 #include <ObjexxFCL/Star.hh>
351 #include <ObjexxFCL/StaticIndexRange.fwd.hh>
352 #include <ObjexxFCL/StaticIndexRange.hh>
353 #include <ObjexxFCL/TypeTraits.hh>
354 #include <ObjexxFCL/char.functions.hh>
355 #include <ObjexxFCL/proxy_const_assert.hh>
356 #include <ObjexxFCL/string.functions.hh>
357 #include <algorithm>
358 #include <cassert>
359 #include <cmath>
360 #include <cstddef>
361 #include <cstdio>
362 #include <cstdlib>
363 #include <iomanip>
364 #include <iosfwd>
365 #include <iostream>
366 #include <limits>
367 #include <map>
368 #include <ostream>
369 #include <set>
370 #include <sstream>
371 #include <string>
372 #include <typeinfo>
373 #include <utility>
374 #include <vector>
375 #include <basic/MetricValue.fwd.hh>
376 #include <basic/datacache/BasicDataCache.fwd.hh>
377 #include <basic/options/keys/OptionKeys.hh>
378 #include <basic/options/option.hh>
379 #include <boost/algorithm/string/erase.hpp>
380 #include <boost/bind.hpp>
381 #include <boost/foreach.hpp>
382 #include <boost/function.hpp>
383 #include <boost/functional/hash.hpp>
384 #include <boost/unordered/unordered_map.hpp>
385 
386 //Auto Headers
387 #define foreach BOOST_FOREACH
388 
389 namespace core {
390 namespace scoring {
391 
392 template< class T >
395  core::pose::Pose const & pose1,
396  core::pose::Pose const & pose2,
397  std::list< core::Size > const & subset_residues,
398  T* predicate
399 )
400 {
401  ASSERT_ONLY(core::Size const nres1 = pose1.total_residue();)
402  ASSERT_ONLY(core::Size const nres2 = pose2.total_residue();)
403  assert( nres1 == nres2 );
404 
405  std::vector< core::Vector > p1_coords;
406  std::vector< core::Vector > p2_coords;
407 
408  foreach(Size i, subset_residues){
409  Size num_atoms ( pose1.residue(i).natoms() );
410  if ( predicate == is_ligand_heavyatom ||
411  predicate == is_polymer_heavyatom ||
412  predicate == is_heavyatom ) {
413  // assert( pose1.residue(i).nheavyatoms() == pose2.residue(i).nheavyatoms() );
414  } else if ( num_atoms > pose2.residue(i).natoms() ){
415  num_atoms = pose2.residue(i).natoms();
416  }
417  for ( core::Size j = 1; j <= num_atoms; ++j ) {
418  if( j <= pose1.residue(i).natoms() &&
419  j <= pose2.residue(i).natoms() ) {
420  if ( predicate( pose1, pose2, i, j ) ) {
421  p1_coords.push_back( pose1.residue(i).xyz(j) );
422  p2_coords.push_back( pose2.residue(i).xyz(j) );
423  }
424  }
425  }
426  }
427  assert( p1_coords.size() == p2_coords.size() );
428 
429  int const natoms = p1_coords.size();
430  ObjexxFCL::FArray2D< core::Real > p1a( 3, natoms );
431  ObjexxFCL::FArray2D< core::Real > p2a( 3, natoms );
432  for ( int i = 0; i < natoms; ++i ) {
433  for ( int k = 0; k < 3; ++k ) { // k = X, Y and Z
434  p1a(k+1,i+1) = p1_coords[i][k];
435  p2a(k+1,i+1) = p2_coords[i][k];
436  }
437  }
438 
439  return numeric::model_quality::rms_wrapper( natoms, p1a, p2a );
440 }
441 
442 /// @brief Select atoms for RMS via a predicate function/functor.
443 /// @details Calculates minimal rms, allowing rotation/translation for best fit.
444 /// Parameter "predicate" should be a function pointer
445 /// [ or class that defines operator() ] with the following signature:
446 ///
447 /// bool my_pred_func(Pose const & pose1, Pose const & pose2, Size resno, Size atomno);
448 ///
449 /// It should return true if the atom should be included and false otherwise.
450 ///
451 /// Example of use, to calculate C-alpha RMSD:
452 /// rmsd_with_super(pose1, pose2, is_protein_CA);
453 template< class T >
456  core::pose::Pose const & pose1,
457  core::pose::Pose const & pose2,
458  T* predicate
459 )
460 {
461  std::list< core::Size > all_residues;
462  for (core::Size n = 1; n <= pose1.total_residue(); n++ ){
463  all_residues.push_back( n );
464  }
465  return rmsd_with_super( pose1, pose2, all_residues, predicate );
466 }
467 
468 
469 
470 /// @brief Select a subset atoms for RMS via a predicate function/functor.
471 /// @details Calculates minimal rms, allowing rotation/translation for best fit.
472 /// Same as above function, but allows a subset of residues over which to
473 /// superposition to be passed in
474 /// Parameter "predicate" should be a function pointer
475 /// [ or class that defines operator() ] with the following signature:
476 ///
477 /// bool my_pred_func(Pose const & pose1, Pose const & pose2, Size resno, Size atomno);
478 ///
479 /// It should return true if the atom should be included and false otherwise.
480 ///
481 /// Example of use, to calculate C-alpha RMSD:
482 /// rmsd_with_super(pose1, pose2, is_protein_CA, subset);
483 template< class T >
486  core::pose::Pose const & pose1,
487  core::pose::Pose const & pose2,
488  ObjexxFCL::FArray1D_bool const & subset,
489  T* predicate
490 )
491 {
492  core::Size const nres1 = pose1.total_residue();
493  //core::Size const nres2 = pose2.total_residue();
494  //assert( nres1 == nres2 );
495 
496  std::vector< core::Vector > p1_coords;
497  std::vector< core::Vector > p2_coords;
498 
499  for ( core::Size i = 1; i <= nres1; ++i ) {
500  if ( subset( i ) ) {
501  Size num_atoms ( pose1.residue(i).natoms() );
502  if ( predicate == is_ligand_heavyatom ||
503  predicate == is_polymer_heavyatom ||
504  predicate == is_heavyatom ) {
505  assert( pose1.residue(i).natoms() == pose2.residue(i).natoms() );
506  } else if ( num_atoms > pose2.residue(i).natoms() ){
507  num_atoms = pose2.residue(i).natoms();
508  }
509  for ( core::Size j = 1; j <= num_atoms; ++j ) {
510  if ( predicate( pose1, pose2, i, j ) ) {
511  p1_coords.push_back( pose1.residue(i).xyz(j) );
512  p2_coords.push_back( pose2.residue(i).xyz(j) );
513  }
514  }
515  }
516  }
517  assert( p1_coords.size() == p2_coords.size() );
518 
519  int const natoms = p1_coords.size();
520  ObjexxFCL::FArray2D< core::Real > p1a( 3, natoms );
521  ObjexxFCL::FArray2D< core::Real > p2a( 3, natoms );
522  for ( int i = 0; i < natoms; ++i ) {
523  for ( int k = 0; k < 3; ++k ) { // k = X, Y and Z
524  p1a(k+1,i+1) = p1_coords[i][k];
525  p2a(k+1,i+1) = p2_coords[i][k];
526  }
527  }
528 
529  return numeric::model_quality::rms_wrapper( natoms, p1a, p2a );
530 }
531 
532 
533 /// @brief Select atoms for RMS via a predicate function/functor.
534 /// @details Calculates minimal rms, NOT allowing rotation/translation --
535 /// uses current coordinates as-is.
536 /// Parameter "predicate" should be a function pointer
537 /// [ or class that defines operator() ] with the following signature:
538 ///
539 /// bool my_pred_func(Pose const & pose1, Pose const & pose2, Size resno, Size atomno);
540 ///
541 /// It should return true if the atom should be included and false otherwise.
542 ///
543 /// Example of use, to calculate C-alpha RMSD:
544 /// rmsd_no_super(pose1, pose2, is_protein_CA);
545 template< class T >
548  core::pose::Pose const & pose1,
549  core::pose::Pose const & pose2,
550  T* predicate
551 )
552 {
553  core::Size const nres1 = pose1.total_residue();
554  ASSERT_ONLY(core::Size const nres2 = pose2.total_residue();)
555  assert( nres1 == nres2 );
556 
557  core::Real sum2( 0.0 );
558  core::Size natoms( 0 );
559  for ( core::Size i = 1; i <= nres1; ++i ) {
560  Size num_atoms ( pose1.residue(i).natoms() );
561  if ( predicate == is_ligand_heavyatom ||
562  predicate == is_polymer_heavyatom ||
563  predicate == is_heavyatom ) {
564  assert( pose1.residue(i).natoms() == pose2.residue(i).natoms() );
565  } else if ( num_atoms > pose2.residue(i).natoms() ){
566  num_atoms = pose2.residue(i).natoms();
567  }
568  for ( core::Size j = 1; j <= num_atoms; ++j ) {
569  if ( predicate( pose1, pose2, i, j ) ) {
570  core::Vector diff = pose1.residue(i).xyz(j) - pose2.residue(i).xyz(j);
571  sum2 += diff.length_squared();
572  natoms += 1;
573  }
574  }
575  }
576  return std::sqrt(sum2 / natoms);
577 }
578 
579 template< class T >
582  core::conformation::ResidueCOPs const & residues1,
583  core::conformation::ResidueCOPs const & residues2,
584  T* predicate
585 )
586 {
587  core::Size const nres1 = residues1.size();
588  ASSERT_ONLY(core::Size const nres2 = residues2.size();)
589  assert( nres1 == nres2 );
590 
591  core::Real sum2( 0.0 );
592  core::Size natoms( 0 );
593  for ( core::Size i = 1; i <= nres1; ++i ) {
594  Size num_atoms ( residues1[i]->natoms() );
595  if ( predicate == is_ligand_heavyatom_residues
596  /* predicate == is_polymer_heavyatom || */
597  /* predicate == is_heavyatom */) { // for Rotate.cc
598  assert( residues1[i]->natoms() == residues2[i]->natoms() );
599  } else if ( num_atoms > residues2[i]->natoms() ){
600  num_atoms = residues2[i]->natoms();
601  }
602  for ( core::Size j = 1; j <= num_atoms; ++j ) {
603  if ( predicate( *residues1[i], *residues2[i], j ) ) {
604  core::Vector diff = residues1[i]->xyz(j) - residues2[i]->xyz(j);
605  sum2 += diff.length_squared();
606  natoms += 1;
607  }
608  }
609  }
610  return std::sqrt(sum2 / natoms);
611 }
612 
613 /// @brief Select atoms for RMS via a predicate function/functor.
614 /// @details Calculates minimal rms over a subset of residues,
615 /// NOT allowing rotation/translation --
616 /// uses current coordinates as-is.
617 /// Parameter "predicate" should be a function pointer
618 /// [ or class that defines operator() ] with the following signature:
619 ///
620 /// bool my_pred_func(Pose const & pose1, Pose const & pose2, Size resno, Size atomno);
621 /// the subset is a vector of all the residues, with true for those
622 /// over which to calculate the rms
623 ///
624 /// It should return true if the atom should be included and false otherwise.
625 ///
626 /// Example of use, to calculate C-alpha RMSD:
627 /// rmsd_no_super_subset(pose1, pose2, subset, is_protein_CA);
628 template< class T >
631  core::pose::Pose const & pose1,
632  core::pose::Pose const & pose2,
633  ObjexxFCL::FArray1D_bool const & subset,
634  T* predicate
635 )
636 {
637  core::Size const nres1 = pose1.total_residue();
638  ASSERT_ONLY(core::Size const nres2 = pose2.total_residue();)
639  assert( nres1 == nres2 );
640 
641  core::Real sum2( 0.0 );
642  core::Size natoms( 0 );
643  for ( core::Size i = 1; i <= nres1; ++i ) {
644  if ( subset( i ) ) {
645  Size num_atoms ( pose1.residue(i).natoms() );
646  if ( predicate == is_ligand_heavyatom ||
647  predicate == is_polymer_heavyatom ||
648  predicate == is_heavyatom ) {
649  assert( pose1.residue(i).natoms() == pose2.residue(i).natoms() );
650  } else if ( num_atoms > pose2.residue(i).natoms() ){
651  num_atoms = pose2.residue(i).natoms();
652  }
653  for ( core::Size j = 1; j <= num_atoms; ++j ) {
654  if ( predicate( pose1, pose2, i, j ) ) {
655  core::Vector diff = pose1.residue(i).xyz(j) - pose2.residue(i).xyz(j);
656  sum2 += diff.length_squared();
657  natoms += 1;
658  }
659  }
660  }
661  }
662  return std::sqrt(sum2 / natoms);
663 }
664 
665 /// @brief function to return the biggest deviation between an atom in a pair of poses,
666 template< class T >
669  core::pose::Pose const & pose1,
670  core::pose::Pose const & pose2,
671  T* predicate
672 ){
673 
674  core::Size const nres1 = pose1.total_residue();
675  ASSERT_ONLY(core::Size const nres2 = pose2.total_residue();)
676  assert( nres1 == nres2 );
677 
678  core::Real biggest_dev2( 0.0 );
679  for ( core::Size i = 1; i <= nres1; ++i ) {
680 
681  Real res_dev2(0.0);
682  Size res_count_atoms(0);
683  Size num_atoms ( pose1.residue(i).natoms() );
684  if ( predicate == is_ligand_heavyatom ||
685  predicate == is_polymer_heavyatom ||
686  predicate == is_heavyatom ) {
687  assert( pose1.residue(i).natoms() == pose2.residue(i).natoms() );
688  } else if ( num_atoms > pose2.residue(i).natoms() ){
689  num_atoms = pose2.residue(i).natoms();
690  }
691  for ( core::Size j = 1; j <= num_atoms; ++j ) {
692  if ( predicate( pose1, pose2, i, j ) ) {
693  core::Vector diff = pose1.residue(i).xyz(j) - pose2.residue(i).xyz(j);
694  res_dev2 += diff.length_squared();
695  res_count_atoms++;
696  }
697  }
698  res_dev2 /= res_count_atoms;
699  if( res_dev2 > biggest_dev2 ) biggest_dev2 = res_dev2;
700  }
701  return std::sqrt( biggest_dev2 );
702 }
703 
704 
705 /// @brief function to return the biggest deviation between an atom in a pair of poses,
706 /// @brief as specified by the predicate and the subset
707 template< class T >
710  core::pose::Pose const & pose1,
711  core::pose::Pose const & pose2,
712  ObjexxFCL::FArray1D_bool const & subset,
713  T* predicate
714 ){
715 
716  core::Size const nres1 = pose1.total_residue();
717  ASSERT_ONLY(core::Size const nres2 = pose2.total_residue());
718  assert( nres1 == nres2 );
719 
720  core::Real biggest_dev2( 0.0 );
721  for ( core::Size i = 1; i <= nres1; ++i ) {
722  if ( subset( i ) ) {
723  Real res_dev2(0.0);
724  Size res_count_atoms(0);
725  Size num_atoms ( pose1.residue(i).natoms() );
726  if ( predicate == is_ligand_heavyatom ||
727  predicate == is_polymer_heavyatom ||
728  predicate == is_heavyatom ) {
729  assert( pose1.residue(i).natoms() == pose2.residue(i).natoms() );
730  } else if ( num_atoms > pose2.residue(i).natoms() ){
731  num_atoms = pose2.residue(i).natoms();
732  }
733  for ( core::Size j = 1; j <= num_atoms; ++j ) {
734  if ( predicate( pose1, pose2, i, j ) ) {
735  core::Vector diff = pose1.residue(i).xyz(j) - pose2.residue(i).xyz(j);
736  res_dev2 += diff.length_squared();
737  res_count_atoms++;
738  }
739  }
740  res_dev2 /= res_count_atoms;
741  if( res_dev2 > biggest_dev2 ) biggest_dev2 = res_dev2;
742  }
743  }
744  return std::sqrt( biggest_dev2 );
745 }
746 
747 template< class T >
748 void
750  int & natoms,
751  ObjexxFCL::FArray2D< core::Real > & p1a,
752  ObjexxFCL::FArray2D< core::Real > & p2a,
753  core::pose::Pose const & pose1,
754  core::pose::Pose const & pose2,
755  T* predicate
756 )
757 {
758  core::Size const nres1 = pose1.total_residue();
759  core::Size const nres2 = pose2.total_residue();
760  //assert( nres1 == nres2 );
761 
762  std::vector< core::Vector > p1_coords;
763  std::vector< core::Vector > p2_coords;
764 
765  for ( core::Size i = 1; i <= std::min( nres1, nres2 ); ++i ) {
766  if( pose1.residue(i).is_virtual_residue() || pose2.residue(i).is_virtual_residue() ) continue;
767  //assert( pose1.residue(i).natoms() == pose2.residue(i).natoms() );
768  for ( core::Size j = 1; j <= pose1.residue(i).natoms(); ++j ) {
769  if ( (*predicate)( pose1, pose2, i, j ) ) {
770  p1_coords.push_back( pose1.residue(i).xyz(j) );
771  p2_coords.push_back( pose2.residue(i).xyz(j) );
772  }
773  }
774  }
775  assert( p1_coords.size() == p2_coords.size() );
776 
777  natoms = p1_coords.size();
778  p1a.dimension( 3, natoms );
779  p2a.dimension( 3, natoms );
780  for ( int i = 0; i < natoms; ++i ) {
781  for ( int k = 0; k < 3; ++k ) { // k = X, Y and Z
782  p1a(k+1,i+1) = p1_coords[i][k];
783  p2a(k+1,i+1) = p2_coords[i][k];
784  }
785  }
786 }
787 
788 /// @brief Select a subset atoms for Symmetric RMS via a predicate function/functor.
789 /// Example of use, to calculate C-alpha RMSD:
790 /// rmsd_with_super(pose1, pose2, is_protein_CA, subset);
791 template< class T >
794  core::pose::Pose const & native_pose,
795  core::pose::Pose const & pose2,
796  ObjexxFCL::FArray1D_bool const & subset,
797  T* predicate
798 )
799 {
800  core::Size const nres1 = native_pose.total_residue();
801  //core::Size const nres2 = pose2.total_residue();
802  //assert( nres1 == nres2 );
803 
804  std::vector< core::Vector > p1_coords;
805  std::vector< core::Vector > p2_coords;
806 
807  for ( core::Size i = 1; i <= nres1; ++i ) {
808  if ( subset( i ) ) {
809  Size num_atoms ( native_pose.residue(i).natoms() );
810  if ( predicate == is_ligand_heavyatom ||
811  predicate == is_polymer_heavyatom ||
812  predicate == is_heavyatom ) {
813  assert( native_pose.residue(i).natoms() == pose2.residue(i).natoms() );
814  } else if ( num_atoms > pose2.residue(i).natoms() ){
815  num_atoms = pose2.residue(i).natoms();
816  }
817  for ( core::Size j = 1; j <= num_atoms; ++j ) {
818  if ( predicate( native_pose, pose2, i, j ) ) {
819  p1_coords.push_back( native_pose.residue(i).xyz(j) );
820  p2_coords.push_back( pose2.residue(i).xyz(j) );
821  }
822  }
823  }
824  }
825  assert( p1_coords.size() == p2_coords.size() );
826 
827  int const natoms = p1_coords.size();
828  ObjexxFCL::FArray2D< core::Real > p1a( 3, natoms );
829  ObjexxFCL::FArray2D< core::Real > p2a( 3, natoms );
830  for ( int i = 0; i < natoms; ++i ) {
831  for ( int k = 0; k < 3; ++k ) { // k = X, Y and Z
832  p1a(k+1,i+1) = p1_coords[i][k];
833  p2a(k+1,i+1) = p2_coords[i][k];
834  }
835  }
836 
837 
838  assert( dynamic_cast< core::conformation::symmetry::SymmetricConformation const * >( &pose2.conformation() ) );
839 
841  dynamic_cast<core::conformation::symmetry::SymmetricConformation const & > ( pose2.conformation()) );
843 
844  int const N ( symm_info->subunits() );
845  int const nres ( symm_info->num_total_residues_without_pseudo() );
846  FArray2D< core::Real > p1a_shuffle( 3, nres );
847 
848  core::Real rms = 1e3; //Since fast_rms has not been evaluated yet
849  int const num_atoms_subunit (natoms);
850  std::vector< std::vector<int> > shuffle_map;
851  create_shuffle_map_recursive_rms(std::vector<int>(), N,shuffle_map);
852  for (int j=1; j < int (shuffle_map.size()); j++ ){
853  for (int i=0; i < N; ++i ) {
854  int const begin ( shuffle_map.at(j).at(i)*num_atoms_subunit*3);
855  for ( int k = 0; k < num_atoms_subunit*3; ++k ) {
856  int const begin_shuffled (i*num_atoms_subunit*3);
857  p1a_shuffle[begin_shuffled+k] = p1a[begin+k];
858  }
859  }
860  Real rms_shuffle = numeric::model_quality::rms_wrapper( natoms, p1a_shuffle, p2a );
861  if ( rms_shuffle < rms ) {
862  rms = rms_shuffle;
863  }
864  }
865  return rms;
866 }
867 
868 } // end namespace scoring
869 } // end namespace core
870 
871 #endif