Rosetta 3.5
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
SymmetricEnergies.cc
Go to the documentation of this file.
1 // -*- mode:c++;tab-width:2;indent-tabs-mode:t;show-trailing-whitespace:t;rm-trailing-spaces:t -*-
2 // vi: set ts=2 noet:
3 //
4 // This file is part of the Rosetta software suite and is made available under license.
5 // The Rosetta software is developed by the contributing members of the Rosetta Commons consortium.
6 // (C) 199x-2009 Rosetta Commons participating institutions and developers.
7 // For more information, see http://www.rosettacommons.org/.
8 
9 /// @file core/scoring/Energies.cc
10 /// @brief Symmetrical Energies class to store cached energies and track the residue
11 /// neighbor relationships
12 /// @author Ingemar Andre
13 
14 // Unit Headers
16 #include <core/scoring/Energies.hh>
17 
18 // AUTO-REMOVED #include <basic/Tracer.hh>
19 
20 // Package Headers
26 
30 
31 // Project Headers
34 
35 #include <core/pose/Pose.hh>
36 #include <core/pose/util.hh>
37 
38 // AUTO-REMOVED #include <core/id/AtomID_Map.Pose.hh>
39 #include <core/id/AtomID.hh>
40 
41 // Utility headers
42 #include <utility/exit.hh>
43 
46 #include <utility/vector1.hh>
47 
48 //Auto Headers
50 
51 namespace core {
52 namespace scoring {
53 namespace symmetry {
54 
56  Energies()
57 {}
58 
59 /// copy ctor -- deep copy
61  Energies( other )
62 {}
63 
64 /// copy ctor -- deep copy
66  Energies( other )
67 {}
68 
69 /// assignment operator -- deep copy
70 Energies const &
72 {
73  Energies::operator=( rhs );
74  return *this;
75 }
76 
77 bool
78 SymmetricEnergies::same_type_as_me( Energies const & other, bool recurse /* = true */ ) const
79 {
80  if ( ! dynamic_cast< SymmetricEnergies const * > ( &other ) ) {
81  return false;
82  }
83  if ( recurse ) {
84  return other.same_type_as_me( *this, false );
85  } else {
86  return true;
87  }
88 }
89 
90 
91 ///@details make a copy of this Energies( allocate actual memory for it )
94 {
95  return new SymmetricEnergies( *this );
96 }
97 
99 
101 {
102  derivative_graph_ = dg;
103 }
104 
106 {
107  return derivative_graph_;
108 }
109 
111 {
112  return derivative_graph_;
113 }
114 
115 /// @brief Add edges to the energy_graph and the context graphs according to domain map
116 ///
117 /// @details Precondition: if the graph contains any edges, then all neighbor relationships between
118 /// pairs of residues that have not moved relative to each other are represented by the
119 /// presence or absence of edges in the energy graph. If there are no edges in the
120 /// energy graph, then all pair inforamtion must be calculated
121 /// Precondition: if two residues have changed relative to one another according to
122 /// the domain map, then there are no edges between them.
123 void
125  pose::Pose const & pose
126 )
127 {
128  using namespace graph;
129  using namespace scoring;
130 
131  //std::cout << "update_neighbor_links: interaction dist: " << scorefxn_info_->max_atomic_interaction_distance() <<
132  // std::endl;
133 
134  // find SymmInfo
135  SymmetricConformation const & SymmConf (
136  dynamic_cast<SymmetricConformation const &> ( pose.conformation()) );
137  SymmetryInfoCOP symm_info( SymmConf.Symmetry_Info() );
138 
140  if ( pg == 0 ) {
141  pg = new conformation::PointGraph;
142  }
143  fill_point_graph( pose, pg );
144 
145  // According to the domain map, add some of the edges detected by the octree to
146  // the energy graph and to the context graphs
147 
148  bool all_moved( energy_graph_no_state_check().num_edges() == 0 );
149 
150  utility::vector1< ContextGraphOP > context_graphs_present;
151  for ( uint ii = 1, ii_end = context_graphs().size(); ii <= ii_end; ++ii ) {
152  if ( context_graphs()[ ii ] ) context_graphs_present.push_back( context_graphs()[ ii ] );
153  }
154 
155  for ( uint ii = 1, ii_end = pose.total_residue(); ii <= ii_end; ++ii ) {
156 
157  int const ii_map( domain_map_during_minimization(ii) );
158  bool const ii_moved( ii_map == 0 || all_moved );
159 
160  Distance const iiradius( pose.residue_type( ii ).nbr_radius() );
161  Distance const ii_intxn_radius( iiradius +
162  get_scorefxn_info().max_atomic_interaction_distance() );
163 
165  ii_iter = pg->get_vertex( ii ).upper_edge_list_begin(),
166  ii_end_iter = pg->get_vertex( ii ).upper_edge_list_end();
167  ii_iter != ii_end_iter; ++ii_iter ) {
168  uint const jj = ii_iter->upper_vertex();
169  if ( ( domain_map_during_minimization(jj) != ii_map ) || ii_moved ) {
170 
171  Distance const jjradius( pose.residue_type( jj ).nbr_radius() );
172  DistanceSquared const square_distance( ii_iter->data().dsq() );
173 
174  // How about we simply make sure the radii sum is positive instead of paying for a sqrt
175  // if ( std::sqrt( square_distance ) < ( ii_intxn_radius + jj_res.nbr_radius() ) ) {
176  if ( ii_intxn_radius + jjradius > 0 ) {
177  if ( square_distance < (ii_intxn_radius + jjradius )*(ii_intxn_radius + jjradius )) {
178 // bool symm_add;
179 // if (SymmConf.Symmetry_Info().subunits() > 2 ) {
180 // bool symm_add = symm_info.scoring_residue(jj);
181 // } else {
182 // symm_add = ( symm_info.bb_is_independent(jj) )
183 // || ( !symm_info.bb_is_independent(jj) &&
184 // symm_info.bb_follows(jj) <= ii );
185 // }
186 // if ( symm_add ) {
187  energy_graph_no_state_check().add_energy_edge( ii, jj, square_distance );
188 // }
189  }
190  for ( uint kk = 1; kk <= context_graphs_present.size(); ++kk ) {
191  context_graphs_present[ kk ]->conditionally_add_edge( ii, jj, square_distance );
192  }
193  }
194  }
195  }
196  }
197  /// Manually set the neighbour count for the energy_graph to be symmetrical
198  for ( uint res = 1; res <= pose.total_residue(); ++res ) {
199  if ( !SymmConf.Symmetry_Info()->fa_is_independent( res ) ) {
200  int symm_res ( SymmConf.Symmetry_Info()->bb_follows( res ) );
201  int neighbors_symm ( energy_graph_no_state_check().get_node( symm_res )->num_neighbors_counting_self() );
203  }
204  }
205  /// Manually set the neighbour count for the energy_graph to be symmetrical
206  for ( uint res = 1; res <= pose.total_residue(); ++res ) {
207  for ( uint kk = 1; kk <= context_graphs_present.size(); ++kk ) {
208  if ( !SymmConf.Symmetry_Info()->fa_is_independent( res ) ) {
209  int symm_res ( SymmConf.Symmetry_Info()->bb_follows( res ) );
210  int neighbors_symm ( context_graphs_present[ kk ]->get_node( symm_res )->num_neighbors_counting_self() );
211  context_graphs_present[ kk ]->get_node( res )->set_num_neighbors_counting_self_static( neighbors_symm );
212  }
213  }
214  }
215 }
216 
217 
218 /// @brief determine distance cutoff threshold based on scorefxn_info_ and
219 /// then add edges to the PointGraph class
220 void
222 
223  SymmetricConformation const & SymmConf (
224  dynamic_cast<SymmetricConformation const &> ( pose.conformation()) );
225  SymmetryInfoCOP symm_info( SymmConf.Symmetry_Info() );
226 
228 
229  Distance const max_pair_radius = pose::pose_max_nbr_radius( pose );
230  Distance const energy_neighbor_cutoff = 2 * max_pair_radius + get_scorefxn_info().max_atomic_interaction_distance();
231 
232  Distance const context_cutoff = max_context_neighbor_cutoff();
233 
234  Distance const neighbor_cutoff = numeric::max( energy_neighbor_cutoff, context_cutoff );
235 
236  // Stuarts O( n log n ) octree algorithm
237  core::conformation::find_neighbors_restricted<core::conformation::PointGraphVertexData,core::conformation::PointGraphEdgeData>( pg, neighbor_cutoff, symm_info->independent_residues() );
238 }
239 
240 /// @brief Create a context graph. If the requirement is external, someone other than a ScoreFunction
241 /// has declared that the context graph is needed (possibly by asking for it right now) so the graph
242 /// must also be made up-to-date.
243 void
245 {
246  //utility::vector1< ContextGraphOP > cgraphs( context_graphs() );
248  utility::vector1< bool >& required_cgraphs( required_context_graphs() );
249  assert( cgraphs[type] == 0 );
250  required_cgraphs[type] = true;
251  cgraphs[type] = ContextGraphFactory::create_context_graph( type );
252  if ( cgraphs[type] == 0 ) {
253  utility_exit_with_message( "Error: Null returned from ContextGraphFactory::create_context_graph( " + utility::to_string( type ) + ")" );
254  }
255  cgraphs[type]->set_num_nodes( size() );
256 
257  if ( max_context_neighbor_cutoff() < cgraphs[type]->neighbor_cutoff() ) {
258  set_max_context_neighbor_cutoff( cgraphs[type]->neighbor_cutoff() );
259  }
260 
261  if ( external ) {
262  required_cgraphs[type] = true;
263 
264  using namespace graph;
265 
268  for ( uint ii = 1, ii_end = size(); ii <= ii_end; ++ii ) {
270  ii_iter = point_graph->get_vertex( ii ).upper_edge_list_begin(),
271  ii_end_iter = point_graph->get_vertex( ii ).upper_edge_list_end();
272  ii_iter != ii_end_iter; ++ii_iter ) {
273  uint const jj = ii_iter->upper_vertex();
274  DistanceSquared const square_distance( ii_iter->data().dsq() );
275  cgraphs[type]->conditionally_add_edge( ii, jj, square_distance );
276  }
277  }
278  }
279  SymmetricConformation const & SymmConf (
280  dynamic_cast<SymmetricConformation const &> ( (*owner()).conformation()) );
281  SymmetryInfoCOP symm_info( SymmConf.Symmetry_Info() );
282 
283  /// Manually set the neighbour count for the context_graph to be symmetrical
284  for ( uint res = 1; res <= (*owner()).total_residue(); ++res ) {
285  if ( !SymmConf.Symmetry_Info()->fa_is_independent( res ) ) {
286  int symm_res ( SymmConf.Symmetry_Info()->bb_follows( res ) );
287  int neighbors_symm ( cgraphs[ type ]->get_node( symm_res )->num_neighbors_counting_self() );
288  cgraphs[ type ]->get_node( res )->set_num_neighbors_counting_self_static( neighbors_symm );
289  }
290  }
291 
292 
293 }
294 
295 
296 } // namespace symmetry
297 } // namespace scoring
298 } // namespace core