Rosetta 3.5
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
PDDFEnergy.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 // (c) Copyright Rosetta Commons Member Institutions.
5 // (c) This file is part of the Rosetta software suite and is made available under license.
6 // (c) The Rosetta software is developed by the contributing members of the Rosetta Commons.
7 // (c) For more information, see http://www.rosettacommons.org. Questions about this can be
8 // (c) addressed to University of Washington UW TechTransfer, email: license@u.washington.edu.
9 
10 /// @file core/scoring/saxs/PDDFEnergy.cc
11 /// @brief "Energy" based on a similarity of theoretical PDDF (pairwise distance distribution function)
12 /// @author Dominik Gront (dgront@chem.uw.edu.pl)
13 
14 
15 // Unit headers
20 
23 
24 // Project headers
25 #include <core/pose/Pose.hh>
28 // AUTO-REMOVED #include <core/id/NamedAtomID.hh>
29 // AUTO-REMOVED #include <core/io/pdb/pose_io.hh>
30 
31 #include <numeric/interpolation/spline/Interpolator.hh>
32 // AUTO-REMOVED #include <numeric/interpolation/spline/SplineGenerator.hh>
33 
34 // Options
35 #include <basic/options/option.hh>
36 #include <basic/options/keys/OptionKeys.hh>
37 #include <basic/options/keys/in.OptionKeys.gen.hh>
38 #include <basic/options/keys/score.OptionKeys.gen.hh>
39 
41 
42 
43 // Utility headers
44 #include <basic/prof.hh>
45 // AUTO-REMOVED #include <basic/database/open.hh>
46 #include <basic/Tracer.hh>
47 #include <utility/io/izstream.hh>
48 #include <utility/exit.hh>
49 
50 // C++
51 #include <iomanip>
52 
54 #include <core/kinematics/Jump.hh>
56 #include <utility/vector1.hh>
57 
58 
59 namespace protocols {
60 namespace scoring {
61 namespace methods {
62 namespace saxs {
63 
64 static basic::Tracer trPDDFEnergy("protocols.scoring.methods.saxs.PDDFEnergy");
65 
68  sts.push_back( core::scoring::pddf_score );
69  return sts;
70 }
71 
73 
74  return new PDDFEnergy();
75 }
76 
77 /// c-tors
79 
80  if_fit_area_ = false;
81  d_.clear();
82  reference_pddf_.clear();
83  for(core::Size i=1;i<=reference_pddf.size();i++) {
84  d_.push_back( reference_d[i] );
85  reference_pddf_.push_back(reference_pddf[i]);
86  }
87  pose_pddf_.resize( d_.size(), 0 );
88  bin_size_ = (d_[ d_.size() ] - d_[1] ) / (d_.size() - 1);
89  min_bin_ = (core::Size)(d_[1] / bin_size_);
90  max_bin_ = (core::Size)(d_[d_.size()] / bin_size_);
91  if(max_bin_ > reference_pddf_.size())
92  max_bin_ = reference_pddf_.size();
93 }
94 
96 
97  using namespace basic::options;
98  using namespace basic::options::OptionKeys;
99 
100  norm_ = 1000.0;
101  if_hydrogens_ = false;
102  if_fit_area_ = false;
103 
104 /*
105  ff_manager_ = FormFactorManager::get_manager();
106  if ( basic::options::option[score::saxs::custom_ff].user() ) {
107  trPDDFEnergy << "Loading custom FF from "<<basic::options::option[score::saxs::custom_ff]()<<std::endl;
108  ff_manager_->load_ff( basic::options::option[score::saxs::custom_ff]() );
109  } else {
110  ff_manager_->load_ff(basic::database::full_name( "scoring/score_functions/saxs/ff-rosetta.cfg" ));
111  }
112 
113 */
114  if( basic::options::option[score::saxs::fit_pddf_area]() )
115  if_fit_area_ = true;
116 
117  core::Real min_d = basic::options::option[score::saxs::d_min]();
118  core::Real max_d = basic::options::option[score::saxs::d_max]();
119  core::Real bin_d = basic::options::option[score::saxs::d_step]();
120 
121  if(option[score::saxs::ref_pddf].user()) {
122  std::string file = option[score::saxs::ref_pddf]();
123 
124  trPDDFEnergy << "Reading reference PDDF: " << file << std::endl;
125  read_pddf(file);
126  min_bin_ = (core::Size)(min_d / bin_size_); //These should be static casts not c style casts
127  max_bin_ = (core::Size)(max_d / bin_size_);
128  if(max_bin_ > reference_pddf_.size())
129  max_bin_ = reference_pddf_.size();
130  } else {
131  bin_size_ = bin_d;
132  if(option[in::file::native].user()) {
133 
134  core::pose::Pose reference_pose;
135  trPDDFEnergy << "Using "<<basic::options::option[in::file::native]()<<" as a reference"<<std::endl;
138  basic::options::option[ in::file::residue_type_set ]());
139 
140  core::import_pose::pose_from_pdb(reference_pose, *rsd_set,
141  basic::options::option[in::file::native]());
142 
144 
145  create_pddf( reference_pose,min_d,bin_d,max_d );
146  min_bin_ = (core::Size)(min_d / bin_size_); //These should be static casts not c style casts
147  max_bin_ = (core::Size)(max_d / bin_size_);
148  } else {
149  utility_exit_with_message( "[ERROR] Unable to load reference PDDF: " );
150  }
151  }
152 }
153 
154 
156  core::scoring::EnergyMap & totals ) const {
157 
158  PROF_START( basic::SAXS );
160 // totals[ pddf_score ] = compute_L1(pose_intensities,reference_intensities_);
162  PROF_STOP( basic::SAXS );
163 }
164 
166 
169 }
170 
171 
173 
174  d_.clear();
175  bin_size_ = d_step;
176  for(core::Real d=d_min;d<=d_max;d+=d_step)
177  d_.push_back(d);
178  pose_pddf_.resize(d_.size());
179  reference_pddf_.resize(d_.size(),0.0);
180 
181  compute_pddf_without_ff(ref_pose);
182 
183  for(core::Size i=1;i<=pose_pddf_.size();i++)
184  reference_pddf_.push_back(pose_pddf_[i]);
185 }
186 
188 
189  d_.clear();
190  reference_pddf_.clear();
191  core::Real tX,tY;
192  utility::io::izstream input(file_name.c_str());
193  if ( !input.good() )
194  utility_exit_with_message( "Unable to open reference spectrum file: " + file_name );
195  std::string line;
196  core::Real norm = 0.0;
197  while( getline( input, line ) ) {
198  if ( line.substr(0,1) == "#" ) continue;
199  if ( line.length() < 4 ) continue;
200  std::istringstream line_stream( line );
201  line_stream >> tX >> tY;
202  d_.push_back( tX );
203  reference_pddf_.push_back( tY );
204  norm += tY;
205  trPDDFEnergy.Trace << "Reference PDDF data: "<<tX<<" "<<tY<<std::endl;
206  }
207 
208  pose_pddf_.resize( d_.size(), 0 );
209  bin_size_ = (d_[ d_.size() ] - d_[1] ) / (d_.size() - 1);
210 
211 // trPDDFEnergy.Debug << "Changing reference PDDF normalisation from: "<<norm<<" to "<<norm_<<std::endl;
212 // norm = norm_ / norm;
213 // for(Size i=1;i<=reference_pddf_.size();i++)
214 // reference_pddf_[i] *= norm;
215 }
216 
218 
219  a_ids_.clear();
220  r_ids_.clear();
221  for(core::Size i=1;i<= pose_pddf_.size();i++) {
222  pose_pddf_[i] = 0.0;
223  }
224  /*********** Rehashing atoms, preparig data structure ************/
225  for ( core::Size i = 1; i <= pose.total_residue(); ++i ) {
226  core::conformation::Residue resi = pose.residue(i);
227  for ( core::Size m = 1; m <= resi.natoms(); ++m ) {
228 // trPDDFEnergy.Trace << "rehash: trying "<<resi.atom_type(m).name();
229  if((! if_hydrogens_)&&( resi.atom_type(m).is_hydrogen())) {
230 // trPDDFEnergy.Trace << " rejected hydrogen"<<std::endl;
231  continue;
232  }
233  a_ids_.push_back( m );
234  r_ids_.push_back( i );
235  }
236  }
237  /*********** Compute distance matrix ************/
238  trPDDFEnergy.Debug << "computing PDDF based on "<<r_ids_.size()<<" atoms"<<std::endl;
239  for ( core::Size i = 2; i <= r_ids_.size(); ++i ) {
240  core::Size res_i = r_ids_[i];
241  core::Size atm_i = a_ids_[i];
242  for ( core::Size j = 1; j < i; ++j ) {
243  core::Size res_j = r_ids_[j];
244  core::Size atm_j = a_ids_[j];
245 
246  core::Real d = pose.residue(res_i).xyz(atm_i).distance( pose.residue(res_j).xyz(atm_j) );
247  core::Size bin = ((core::Size)(d/bin_size_))+1;
248  if(bin>reference_pddf_.size())
249  bin = reference_pddf_.size();
250  pose_pddf_[ bin ] ++;
251  }
252  }
253 
254  return pose_pddf_;
255 }
256 
257 
259 
260  /*********** Rehashing atoms, preparig data structure ************/
261  a_ids_.clear();
262  r_ids_.clear();
263  if(factors_.size() == 0) {
264  for ( core::Size i = 1; i <= pose.total_residue(); ++i ) {
265  core::conformation::Residue resi = pose.residue(i);
266  for ( core::Size m = 1; m <= resi.natoms(); ++m ) {
267  trPDDFEnergy.Trace << "rehash: trying "<<resi.atom_type(m).name();
268  if((! if_hydrogens_)&&( resi.atom_type(m).is_hydrogen())) {
269  trPDDFEnergy.Trace << " rejected hydrogen"<<std::endl;
270  continue;
271  }
272  if( ! ff_manager_->is_known_atom( resi.atom_type(m).name() ) ) {
273  trPDDFEnergy.Trace << " rejected unknown"<<std::endl;
274  continue;
275  }
278  for(core::Size i_s=1;i_s<=d_.size();++i_s) {
279  row.push_back(fi->ff(d_[i_s]));
280  }
281  factors_.push_back( row );
282  a_ids_.push_back( m );
283  r_ids_.push_back( i );
284  if( ( resi.atom_type(m).name()[0] == 'C' ) && ( resi.atom_type(m).name()[1] == 'E' ) && ( resi.atom_type(m).name()[2] == 'N' ) ) {
285  is_glob_.push_back(true);
286  trPDDFEnergy.Trace << " .. is glob ..";
287  }
288  else {
289  is_glob_.push_back(false);
290  trPDDFEnergy.Trace << " .. is atom ..";
291  }
292  trPDDFEnergy.Trace << " OK."<<std::endl;
293  }
294  }
295  trPDDFEnergy.Trace << "Found "<<factors_.size()<<" atoms suitable for PDDF computations"<<std::endl;
296 
297  dmatrix_.resize(factors_.size());
298  for(core::Size i=1;i<=dmatrix_.size();i++)
299  dmatrix_[i].resize(dmatrix_.size());
300  }
301 
302  /*********** Compute distance matrix ************/
303  for ( core::Size i = 2; i <= factors_.size(); ++i ) {
304  core::Size res_i = r_ids_[i];
305  core::Size atm_i = a_ids_[i];
306  for ( core::Size j = 1; j < i; ++j ) {
307  core::Size res_j = r_ids_[j];
308  core::Size atm_j = a_ids_[j];
309 
310  core::Real d = pose.residue(res_i).xyz(atm_i).distance( pose.residue(res_j).xyz(atm_j) );
311  pose_pddf_[ ((core::Size)(d/bin_size_)) ] ++;
312  }
313  }
314  return pose_pddf_;
315 }
316 
318 
319  core::Real chi = -1.0;
320  core::Real sum = 0;
321  assert( pddf_scored.size() == pddf_reference.size() );
322  for(core::Size i=1;i<=pddf_scored.size();++i)
323  sum += pddf_reference[i] / pddf_scored[i];
324  core::Real lambda = sum / ((core::Real) pddf_scored.size());
325 
326  trPDDFEnergy.Trace << "Computing PDDF energy:\n";
327  trPDDFEnergy.Trace << " q pose reference\n";
328  for(core::Size i=1;i<=pddf_reference.size();++i) {
329  core::Real tmp = pddf_scored[i] * lambda - pddf_reference[i];
330  if( fabs(tmp) > chi )
331  chi = fabs(tmp);
332  }
333 
334  trPDDFEnergy.Debug << "\nPDDF energy: " << chi << std::endl;
335  return chi;
336 }
337 
338 
340 
341  core::Real chi = 0;
342  assert( pddf_scored.size() == pddf_reference.size() );
343  core::Real lambda = 1.0;
344  if ( if_fit_area_ ) {
345  core::Real sum_scored = 0;
346  core::Real sum_ref = 0;
347  for(core::Size i=min_bin_;i<=max_bin_;++i) {
348  sum_scored += pddf_scored[i];
349  sum_ref += pddf_reference[i];
350  }
351  lambda = sum_ref / sum_scored;
352  }
353 
354  trPDDFEnergy.Trace << "Computing PDDF energy:\n";
355  trPDDFEnergy.Trace << " r_i pose reference avg delta-chi sum-chi\n";
356  core::Real nonzero = 0.0;
357  for(core::Size i=min_bin_;i<=max_bin_;++i) {
358  if( (pddf_scored[i]<0.00001) && ( pddf_reference[i]<0.000001) )
359  continue;
360  nonzero++;
361  core::Real avg = (pddf_scored[i] * lambda + pddf_reference[i]) / 2.0;
362  core::Real tmp = pddf_scored[i] * lambda - pddf_reference[i];
363  chi += tmp*tmp/avg;
364  trPDDFEnergy.Trace << std::setw(9)<<std::setprecision(4)<<d_[i]<<" ";
365  trPDDFEnergy.Trace << std::setw(9)<<std::setprecision(4)<<pddf_scored[i]*lambda<<" ";
366  trPDDFEnergy.Trace << std::setw(9)<<std::setprecision(4)<<pddf_reference[i]<<" ";
367  trPDDFEnergy.Trace << std::setw(9)<<std::setprecision(4)<< avg<<" ";
368  trPDDFEnergy.Trace << std::setw(9)<<std::setprecision(4)<< (tmp*tmp)/avg<<" ";
369  trPDDFEnergy.Trace << std::setw(9)<<std::setprecision(4)<<chi<<"\n";
370  }
371  chi /= nonzero;
372 
373  trPDDFEnergy.Debug << "\nPDDF energy: " << chi << std::endl;
374  return chi;
375 }
378 {
379  return 1; // Initial versioning
380 }
381 
382 
383 } // saxs
384 } // scoring
385 } // methods
386 } // protocols