Rosetta 3.5
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
AtomTypeSet.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 /// @begin AtomTypeSet
11 ///
12 /// @brief
13 /// A class for reading in the atom type properties
14 ///
15 /// @detailed
16 /// This class reads in the atom_properties.txt file which contains the "chemical" information for atoms.
17 /// This does not contain the actual properties, but sets the properties through the AtomType class.
18 /// This class is called by the ChemicalManager
19 ///
20 ///
21 ///
22 /// @authors
23 /// Phil Bradley
24 /// Steven Combs - comments
25 ///
26 ///
27 /// @last_modified December 6 2010
28 /////////////////////////////////////////////////////////////////////////
29 // Unit headers
31 
32 // Project headers
33 #include <basic/Tracer.hh>
34 
35 #include <fstream>
36 #include <iostream>
37 
39 #include <utility/vector1.hh>
40 #include <utility/io/izstream.hh>
41 #include <basic/database/open.hh>
42 #include <basic/database/sql_utils.hh>
43 #include <basic/options/keys/chemical.OptionKeys.gen.hh>
44 #include <basic/options/option.hh>
45 
46 
47 namespace core {
48 namespace chemical {
49 
50 static basic::Tracer tr("core.chemical");
51 
52 
53 ////////////////////////////////////////////////////////////////////////////////
54 
56 {
58 
59  read_file( directory + "/atom_properties.txt" );
60 
61  utility::io::izstream data( ( directory+"/extras.txt" ).c_str() );
62  if ( data.good() ) { // add extra data
63  std::string line;
64  while( getline( data, line ) ) {
65  if ( line.size() && line[0] == '#' ) continue;
66  add_parameters_from_file( directory+"/"+line );
67  }
68  }
69  data.close();
70 
71  if ( basic::options::option[ basic::options::OptionKeys::chemical::enlarge_H_lj ] ) {
73  }
74 }
75 
77  std::string const & name,
78  utility::sql_database::sessionOP db_session) {
79 
80  directory_ = basic::database::full_name( "chemical/atom_type_sets/" + name);
81 
82  { // add atom type to atom type set
83  std::string stmt_string =
84  "SELECT name FROM atom_types WHERE atom_type_set_name = ?;";
85  cppdb::statement stmt(
86  basic::database::safely_prepare_statement(stmt_string, db_session));
87  stmt.bind(1, name);
88  cppdb::result res(basic::database::safely_read_from_database(stmt));
89 
90  std::string atom_type_name;
91  while(res.next()) {
92  res >> atom_type_name;
93  AtomType & atom_type(
95  name, atom_type_name, db_session));
97  name, atom_type, db_session);
99  name, atom_type, db_session);
100  }
101  }
102 
103  { // set the extra parameter indices
104  std::string stmt_string =
105  "SELECT DISTINCT\n"
106  " parameter\n"
107  "FROM\n"
108  " atom_type_extra_parameters\n"
109  "WHERE\n"
110  " atom_type_set_name = ?\n"
111  "ORDER BY\n"
112  " parameter\n";
113  cppdb::statement stmt(
114  basic::database::safely_prepare_statement(stmt_string, db_session));
115  stmt.bind(1, name);
116  cppdb::result res(
117  basic::database::safely_read_from_database(stmt));
118 
120  std::string extra_parameter_name;
121  while(res.next()){
122  res >> extra_parameter_name;
123  extra_parameter_indices_[extra_parameter_name] = extra_parameter_index;
125  }
126  }
127 }
128 
129 
131  // The atoms in the atom type set are kept with raw pointers so they
132  // must be deleted to prevent memory leaks
133  for(Size i=1; i <= atom_type_index_.size(); ++i){
134  delete atoms_[i];
135  }
136 }
137 
138 /// @detail The directory is like '$ROSETTA3_DB/rosetta_database/chemical/atom_type_sets/<atom_type_set_name>/'
139 /// Return 'atom_type_set_name'
140 /// Note: strip off the trailing slash, if it exists
143  Size const last_char_pos(directory_.find_last_not_of('/'));
144  if(last_char_pos == std::string::npos || last_char_pos == 0) return directory_;
145 
146  Size first_char_pos(directory_.find_last_of('/', last_char_pos - 1) + 1);
147  if(first_char_pos == std::string::npos) first_char_pos = 0;
148 
149  return directory_.substr(first_char_pos, last_char_pos - first_char_pos + 1);
150 }
151 
152 /// @brief file I/O
153 ///
154 /// @details initialize an AtomTypeSet from an external file "filename",
155 /// and set parameters and properties for each AtomType.
156 /// Refer to minirosetta_database_stock/chemical/atom_type_sets/fa_standard/atom_properties.txt
157 /// for file format
158 ///
159 void
161 {
162  utility::io::izstream data( filename.c_str() );
163 
164  if ( !data.good() ) utility_exit_with_message( "Unable to open atomset file: "+filename );
165 
166  // parse the header line
168  { // scope
169  std::string line, tag, tag2;
170  getline( data, line );
171  std::istringstream l( line );
172  l >> tag >> tag2;
173  if ( tag != "NAME" || tag2 != "ATOM" ) {
174  utility_exit_with_message("AtomTypeSet::read_file: bad first line: "+ line );
175  }
176  l >> tag;
177  while ( !l.fail() ) {
178  tags.push_back( tag );
179  l >> tag;
180  }
181  }
182 
183  // now parse the rest of the file
184  Size const ntags( tags.size() );
185  {
186  using namespace basic;
187 
188  std::string line, tag, name_wo_whitespace;
189  while ( getline( data,line ) ) {
190  std::istringstream l( line );
191  l >> name_wo_whitespace;
192  if ( l.fail() || name_wo_whitespace.find("#",0) == 0 ) continue; // skip comment,blank lines
193  l >> tag;
194  if ( l.fail() || tag.size() < 1 ) {
195  utility_exit_with_message("bad line: "+line);
196  }
197 
198  // std::string const name( line.substr(0,4) );
199  std::string const element( tag );
200  AtomType* atom_type_ptr( new AtomType( name_wo_whitespace, element ) );
201 
202  // now parse the parameters
203  for ( Size i=1; i<= ntags; ++i ) {
204  Real setting;
205  l >> setting;
206  atom_type_ptr->set_parameter( tags[i], setting );
207  }
208  if ( l.fail() ) {
209  utility_exit_with_message("bad line: "+line);
210  }
211 
212  // now parse the properties
213  l >> tag;
214  while ( !l.fail() && tag.find("#",0) != 0) {
215  atom_type_ptr->set_property( tag, true );
216  l >> tag;
217  }
218 
219  // add this to the list
220  atoms_.push_back( atom_type_ptr );
221  // atom_type_index_[ name ] = atoms_.size();
222  if ( atom_type_index_.count( name_wo_whitespace ) ) {
223  utility_exit_with_message("AtomTypeSet:: duplicate atom name "+name_wo_whitespace);
224  }
225  atom_type_index_[ name_wo_whitespace ] = atoms_.size();
226  tr.Debug << "New atom type: " << name_wo_whitespace << ' ' << element << std::endl; //std::endl;
227  }
228  } // scope
229 
230 
231 }
232 
233 
234 ///////////////////////////////////////////////////////////////////////////////
235 /// @details Private helper function for filling in default values in the fxn add_parameters_from_file
236 /// Enables the user to specify a default parameter set to be used and then provide a few modifications.
237 ///
238 /// eg in the dna_interface lj-radii parameter set we shrink the hydrogens but leave the rest unchanged.
239 ///
240 /// @note This function is very SLOW, but that should be OK we only use it a bit right at the start.
241 Real
242 AtomTypeSet::get_default_parameter( std::string const & param_name, std::string const & atm_name ) const
243 {
244  AtomType const & atom_type( *( atoms_ [ atom_type_index( atm_name ) ] ) );
245  if ( has_extra_parameter( param_name ) ) {
246  return atom_type.extra_parameter( extra_parameter_index( param_name ) );
247  } else {
248  // get hardcoded params from atomtype
249 
250  if ( param_name == "LJ_RADIUS" ) {
251  return atom_type.lj_radius();
252  } else if ( param_name == "LJ_WDEPTH" ) {
253  return atom_type.lj_wdepth();
254  } else if ( param_name == "LK_VOLUME" ) {
255  return atom_type.lk_volume();
256  } else if ( param_name == "LK_DGFREE" ) {
257  return atom_type.lk_dgfree();
258  } else if ( param_name == "LK_LAMBDA" ) {
259  return atom_type.lk_lambda();
260  }
261  }
262  utility_exit_with_message( "unrecognized parameter type: "+param_name );
263  return 0.0; // appease compiler
264 }
265 
266 ///////////////////////////////////////////////////////////////////////////////
267 void
269 {
270 
271  // parse the header line
273 
274  Size const index_offset( extra_parameter_indices_.size() );
275 
276  utility::vector1< std::string > default_parameter_names;
278  { // read all the lines from the file
279  utility::io::izstream data( filename.c_str() );
280 
281  if ( !data.good() ) utility_exit_with_message( "Unable to open atomset parameter file: "+filename );
282  std::string line, tag;
283  while ( getline( data,line ) ) {
284  std::istringstream l( line );
285  l >> tag;
286  if ( l.fail() || tag.size() < 1 || tag[0] == '#' ) continue; // skip blank lines or comments
287 
288  if ( tag == "NAME" ) {
289  l >> tag;
290  while ( !l.fail() ) {
291  if ( tag[0] == '#' ) break;
292  tags.push_back( tag );
293  extra_parameter_indices_[ tag ] = tags.size() + index_offset;
294  l >> tag;
295  }
296  } else if ( tag == "DEFAULT" ) {
297  l >> tag;
298  while ( !l.fail() ) {
299  if ( tag[0] == '#' ) break;
300  default_parameter_names.push_back( tag );
301  l >> tag;
302  }
303  } else {
304  lines.push_back( line );
305  }
306  }
307  data.close();
308  }
309 
310  if ( tags.empty() ) utility_exit_with_message("AtomTypeSet::read_file: missing NAME line");
311  if ( !default_parameter_names.empty() && default_parameter_names.size() != tags.size() ) {
312  std::cout << "AtomTypeSet:: number of params doesnt match number of defaults " <<
313  default_parameter_names.size() << ' ' << tags.size() << std::endl;
314  utility_exit();
315  }
316 
317  // now parse the rest of the file
318  Size const ntags( tags.size() );
319  std::map< std::string, utility::vector1< Real > > all_parameters;
320  {
321  std::string tag, name_wo_whitespace;
322  for ( Size ii=1; ii<= lines.size(); ++ii ) {
323  std::string const & line( lines[ii] );
324  std::istringstream l( line );
325  l >> tag; // name_wo_whitespace
326  if ( tag.find("#",0) == 0 ) continue; // skip comment lines
327 
328  // std::string const name( line.substr(0,4) );
329 
330  // now parse the parameters
331  utility::vector1< Real > parameters;
332  for ( Size i=1; i<= ntags; ++i ) {
333  Real setting;
334  l >> setting;
335  parameters.push_back( setting );
336  }
337  if ( l.fail() || parameters.size() != tags.size() ) {
338  utility_exit_with_message("bad line: "+line);
339  }
340 
341  all_parameters[ tag ] = parameters;
342  } // loop over lines from file
343  }
344 
345  // now fill in the data
346  for ( std::map< std::string, int >::const_iterator
347  iter = atom_type_index_.begin(), iter_end = atom_type_index_.end(); iter != iter_end; ++iter ) {
348  std::string const & name( iter->first );
349  int const atom_index( iter->second );
350 
351  //if ( name.size() < 4 ) continue; // ignore stripped ws versions of the atom names
352  std::map< std::string, utility::vector1< Real > >::const_iterator iter2( all_parameters.find( name ) );
354 
355  std::string paramsrc("UNK");
356  if ( iter2 == all_parameters.end() ) {
357  if ( !default_parameter_names.empty() ) {
358  paramsrc = "from_defaults";
359  for ( Size i=1; i<= default_parameter_names.size(); ++i ) {
360  Real const default_param( get_default_parameter( default_parameter_names[i], name ) );
361  // this output doesnt seem to get written out!? so I added more verbose output below (PB)
362  basic::T("core.chemical.AtomTypeSet") << "Using default parameter " << default_parameter_names[i] << " = " <<
363  default_param << " in place of " << tags[i] << " for atomtype " << name << '\n';
364  params.push_back( default_param );
365  }
366  } else {
367  paramsrc = "from_****";
368  iter2 = all_parameters.find( "****" );
369  if ( iter2 == all_parameters.end() ) {
370  utility_exit_with_message( "no parameters specified for atom type: "+name+" in file "+filename );
371  }
372  params = iter2->second;
373  }
374  } else {
375  paramsrc = "from_file";
376  params = iter2->second;
377  //pbadebug
378  //std::cout << "params " << params << std::endl;
379  }
380  //utility::vector1< Real > const & params( iter2->second );
381  runtime_assert( params.size() == tags.size() );
382  for ( Size i=1; i<= tags.size(); ++i ) {
383  tr.Trace << "setting extra parameter: " << tags[i] << ' ' <<atoms_[ atom_index ]->name() << ' ' <<
384  paramsrc << ' ' << params[i] << std::endl;
385  atoms_[ atom_index ]->set_extra_parameter( i + index_offset, params[i] );
386  }
387  } // loop over atom names in this AtomTypeSet
388 
389 }
390 
391 
392 ///////////////////////////////////////////////////////////////////////////////
393 ///////////////////////////////////////////////////////////////////////////////
394 
395 
396 AtomType &
398  std::string const & atom_type_set_name,
399  std::string const & atom_type_name,
400  utility::sql_database::sessionOP db_session
401 ) {
402  std::string stmt_string =
403  "SELECT\n"
404  " element,\n"
405  " lennard_jones_radius REAL,\n"
406  " lennard_jones_well_depth REAL,\n"
407  " lazaridis_karplus_lambda REAL,\n"
408  " lazaridis_karplus_degrees_of_freedom REAL,\n"
409  " lazaridis_karplus_volume REAL\n"
410  "FROM\n"
411  " atom_types\n"
412  "WHERE\n"
413  " atom_type_set_name = ? AND name = ?;";
414 
415  cppdb::statement stmt(
416  basic::database::safely_prepare_statement(stmt_string, db_session));
417  stmt.bind(1, atom_type_set_name);
418  stmt.bind(2, atom_type_name);
419  cppdb::result res(basic::database::safely_read_from_database(stmt));
420 
421  if(!res.next()) {
422  utility_exit_with_message(
423  "could not find atom '" + atom_type_name + "' in '" +
424  atom_type_set_name + "'.");
425  }
426 
427  std::string element;
428  Real lennard_jones_radius;
429  Real lennard_jones_well_depth;
430  Real lazaridis_karplus_lambda;
431  Real lazaridis_karplus_degrees_of_freedom;
432  Real lazaridis_karplus_volume;
433 
434  res
435  >> element
436  >> lennard_jones_radius
437  >> lennard_jones_well_depth
438  >> lazaridis_karplus_lambda
439  >> lazaridis_karplus_degrees_of_freedom
440  >> lazaridis_karplus_volume;
441 
442  AtomType * atom_type_ptr(new AtomType(atom_type_name, element));
443  atom_type_ptr->set_parameter("LJ_RADIUS", lennard_jones_radius);
444  atom_type_ptr->set_parameter("LJ_WDEPTH", lennard_jones_well_depth);
445  atom_type_ptr->set_parameter("LK_LAMBDA", lazaridis_karplus_lambda);
446  atom_type_ptr->set_parameter("LK_DGFREE", lazaridis_karplus_degrees_of_freedom);
447  atom_type_ptr->set_parameter("LK_VOLUME", lazaridis_karplus_volume);
448 
449  atoms_.push_back(atom_type_ptr);
450  atom_type_index_[atom_type_ptr->name()] = atoms_.size();
451  return *atom_type_ptr;
452 }
453 
454 
455 void
457  std::string const & atom_type_set_name,
458  AtomType & atom_type,
459  utility::sql_database::sessionOP db_session
460 ) {
461  std::string stmt_string =
462  "SELECT\n"
463  " property\n"
464  "FROM\n"
465  " atom_type_properties\n"
466  "WHERE\n"
467  " atom_type_set_name = ? AND name = ?;";
468 
469  cppdb::statement stmt(basic::database::safely_prepare_statement(stmt_string, db_session));
470  stmt.bind(1, atom_type_set_name);
471  stmt.bind(2, atom_type.name());
472  cppdb::result res(basic::database::safely_read_from_database(stmt));
473 
474  std::string property;
475  while(res.next()){
476  res >> property;
477  atom_type.add_property(property);
478  }
479 }
480 
481 void
483  std::string const & atom_type_set_name,
484  AtomType & atom_type,
485  utility::sql_database::sessionOP db_session
486 ) {
487  std::string stmt_string =
488  "SELECT\n"
489  " value\n"
490  "FROM\n"
491  " atom_type_extra_parameters\n"
492  "WHERE\n"
493  " atom_type_set_name = ? AND name = ?\n"
494  "ORDER BY\n"
495  " parameter;";
496 
497  cppdb::statement stmt(basic::database::safely_prepare_statement(stmt_string, db_session));
498  stmt.bind(1, atom_type_set_name);
499  stmt.bind(2, atom_type.name());
500  cppdb::result res(basic::database::safely_read_from_database(stmt));
501 
502  std::string parameter;
503  Real value;
504  Size parameter_index(1);
505  while(res.next()){
506  res >> value;
507  atom_type.set_extra_parameter(parameter_index, value);
508  ++parameter_index;
509  }
510 }
511 
512 //Fang-Chieh Chou 8/10/2012
513 //Use larger LJ_WDEPTH for protons to avoid clashes in RNA
514 void
516 {
517  Size const n_H_atom_type = 5;
518  Real const lj_wdepth = 0.15;
519  std::string const H_names [n_H_atom_type] = {"Hpol", "Hapo", "Haro", "HNbb", "HOH"};
520  for (Size i = 0; i != n_H_atom_type; ++i) {
521  Size const index = atom_type_index( H_names[i] );
522  atoms_[index] -> set_parameter( "LJ_WDEPTH", lj_wdepth );
523  }
524 }
525 
526 } // chemical
527 } // core