Rosetta 3.5
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
standard_mains.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 protocols/jobdist/standard_mains.cc
11 ///
12 /// @brief
13 /// @author Ian W. Davis
14 
15 #include <utility/io/izstream.hh>
17 
19 
20 //#include <core/init.hh>
21 #include <core/types.hh>
22 
23 // AUTO-REMOVED #include <core/sequence/util.hh>
24 // AUTO-REMOVED #include <core/io/pdb/file_data.hh>
25 #include <core/io/pdb/pose_io.hh>
31 // AUTO-REMOVED #include <core/import_pose/pose_stream/util.hh>
32 // AUTO-REMOVED #include <core/import_pose/pose_stream/MetaPoseInputStream.hh>
34 
35 // AUTO-REMOVED #include <core/kinematics/MoveMap.hh>
36 #include <basic/options/option.hh>
37 #include <core/pose/Pose.hh>
38 #include <core/pose/util.hh>
40 #include <basic/datacache/BasicDataCache.hh>
41 #include <basic/datacache/CacheableString.hh>
42 #include <basic/datacache/DiagnosticData.hh>
43 #include <basic/Tracer.hh>
44 
45 // AUTO-REMOVED #include <protocols/viewer/viewers.hh>
47 #include <protocols/moves/Mover.hh>
49 // AUTO-REMOVED #include <protocols/evaluation/RmsdEvaluator.hh>
50 #include <numeric/random/random_permutation.hh>
51 #include <utility/exit.hh>
52 #include <utility/file/FileName.hh>
53 #include <utility/pointer/owning_ptr.hh>
54 #include <core/scoring/rms_util.hh>
57 
59 
60 #include <algorithm>
61 // AUTO-REMOVED #include <ctime>
62 #include <map>
63 #include <string>
64 #if defined(WIN32) || defined(__CYGWIN__)
65  #include <ctime>
66 #endif
67 // option key includes
68 
69 // AUTO-REMOVED #include <basic/options/keys/constraints.OptionKeys.gen.hh>
70 #include <basic/options/keys/out.OptionKeys.gen.hh>
71 #include <basic/options/keys/run.OptionKeys.gen.hh>
72 #include <basic/options/keys/in.OptionKeys.gen.hh>
73 #include <basic/options/keys/score.OptionKeys.gen.hh>
74 
75 //Auto Headers
83 #include <utility/vector0.hh>
84 #include <utility/vector1.hh>
85 #include <utility/file/file_sys_util.hh>
86 
87 
88 namespace protocols {
89 namespace jobdist {
90 
92 
93 basic::Tracer TR("protocols.jobdist.main");
94 static numeric::random::RandomGenerator RG(32342524);
95 ////////////////////////////////////////////////////////////////////////////////////////////////
96 
97 
98 ////////////////////////////////////////////////////////////////////////////////////////////////
100 {
101  using basic::options::option;
102  using utility::vector1;
104  using namespace basic::options::OptionKeys;
105 
106  // concatenate -s and -l flags together to get total list of PDB files
107  vector1< FileName > pdb_file_names;
108  if ( option[ in::file::s ].active() )
109  pdb_file_names = option[ in::file::s ]().vector(); // make a copy (-s)
110 
111  vector1< FileName > list_file_names;
112  if ( option[ in::file::l ].active() )
113  list_file_names = option[ in::file::l ]().vector(); // make a copy (-l)
114  if ( option[ in::file::list ].active() ){
115  vector1< FileName > better_list_file_names;
116  better_list_file_names= option[in::file::list ]().vector(); // make a copy (-list)
117  for(vector1< FileName >::iterator i = better_list_file_names.begin(), i_end = better_list_file_names.end(); i != i_end; ++i) {
118  list_file_names.push_back(*i); // make a copy (-l)
119  }
120  }
121 
122  for(vector1< FileName >::iterator i = list_file_names.begin(), i_end = list_file_names.end(); i != i_end; ++i) {
123  std::string filename( i->name() );
124  utility::io::izstream data( filename.c_str() );
125  if ( !data.good() ) {
126  utility_exit_with_message( "Unable to open file: " + filename + '\n' );
127  }
128  std::string line;
129  while( getline(data, line) ) {
130  pdb_file_names.push_back( FileName(line) );
131  }
132  data.close();
133  }
134 
136  int const nstruct_flag = option[ out::nstruct ];
137  int const nstruct = std::max( 1, nstruct_flag );
138  for(vector1< FileName >::iterator i = pdb_file_names.begin(), i_end = pdb_file_names.end(); i != i_end; ++i) {
139  std::string native_file (i->base()+".native.pdb");
140  //TR << "Looking for native: " << native_file << " ... ";
141  if ( option[ in::file::native ].user() ) {
142  native_file = option[ in::file::native ]().name();
143  } else if ( !utility::file::file_exists(native_file) ) {
144  native_file = i->name();
145  //TR << " not found!" << std::endl;
146  } else {
147  //TR << " found!" << std::endl;
148  }
149 
150  BasicJobOP job = new BasicJob(i->name(), native_file, nstruct);
151  jobs.push_back( job );
152  }
153 
154  return jobs;
155 }
156 
157 ////////////////////////////////////////////////////////////////////////////////////////////////
158 ///@brief Helper function to safely get current output tag that's cached in Pose.
160 {
161  //using core::pose::datacache::CacheableDataType::JOBDIST_OUTPUT_TAG;
162  using basic::datacache::CacheableString;
163 
164  if( !pose.data().has( core::pose::datacache::CacheableDataType::JOBDIST_OUTPUT_TAG ) ) return "NO_OUTPUT_TAG_CACHED_SORRY";
165  runtime_assert( dynamic_cast< CacheableString const *>( &( pose.data().get( core::pose::datacache::CacheableDataType::JOBDIST_OUTPUT_TAG ))));
166  return ( static_cast< CacheableString const &>( pose.data().get( core::pose::datacache::CacheableDataType::JOBDIST_OUTPUT_TAG ))).str();
167 }
168 
169 ////////////////////////////////////////////////////////////////////////////////////////////////
170 ///@brief Helper function to safely get score_map that's cached in Pose.
171 std::map < std::string, core::Real > get_score_map(core::pose::Pose const & pose)
172 {
173  //using core::pose::datacache::CacheableDataType::SCORE_MAP;
174  using basic::datacache::DiagnosticData;
175 
177  std::map < std::string, core::Real > map;
178  map[ "NO_OUTPUT_TAG_CACHED_SORRY" ] = 0.0;
179  return map;
180  }
181  runtime_assert( dynamic_cast< DiagnosticData const *>( &( pose.data().get( core::pose::datacache::CacheableDataType::SCORE_MAP ))));
182  return ( static_cast< DiagnosticData const &>( pose.data().get( core::pose::datacache::CacheableDataType::SCORE_MAP ))).data();
183 }
184 
185 ////////////////////////////////////////////////////////////////////////////////////////////////
186 ///@details Universal IO handler for score, relax and cluster (and hopefully more) executables
187 /// Handles reading/writing of Silent OR PDB files.
189  using namespace basic::options;
190  using namespace basic::options::OptionKeys;
191  option.add_relevant( in::file::centroid_input );
192  option.add_relevant( in::file::fullatom );
193  option.add_relevant( in::file::l );
194  option.add_relevant( in::file::native );
195  option.add_relevant( in::file::s );
196  option.add_relevant( in::file::silent );
197  option.add_relevant( in::file::silent_struct_type );
198  option.add_relevant( in::file::silent_list );
199  option.add_relevant( in::file::tags );
200  option.add_relevant( out::file::scorefile );
201  option.add_relevant( out::file::silent );
202  option.add_relevant( out::nooutput );
203  option.add_relevant( out::nstruct );
204  option.add_relevant( out::prefix );
205  option.add_relevant( run::repeat );
206 }
207 
209  protocols::moves::Mover & mover,
210  float thinout_factor
211 )
212 {
213  using namespace protocols;
214  using namespace protocols::jobdist;
215  using namespace protocols::moves;
216  using namespace core::scoring;
217  using namespace basic::options;
218  using namespace basic::options::OptionKeys;
219  using namespace utility::file;
220  //using core::pose::datacache::CacheableDataType::JOBDIST_OUTPUT_TAG;
221  //using core::pose::datacache::CacheableDataType::MEMBRANE_TOPOLOGY;
222  using basic::datacache::CacheableString;
223 
224  // open native pose if it exists
225  core::pose::Pose native_pose;
226  if (option[ in::file::native ].user()) {
227  core::import_pose::pose_from_pdb( native_pose, option[ in::file::native ]() );
228  // Set the native pose into the mover
229  mover.set_native_pose( new core::pose::Pose(native_pose) );
230 #ifdef BOINC_GRAPHICS
231  // set native for graphics
232  boinc::Boinc::set_graphics_native_pose( native_pose );
233 #endif
234  }
235 
236  /// ---------- SILENT ----------------------------------
237  // Are we reading a silent file here ?
238  if( option[ in::file::silent ].user() || option[ in::file::silent_list ].user() ){
239 
240  // setup residue types
242  if ( option[ in::file::fullatom ]() ) {
244  } else if ( option[ in::file::residue_type_set ]() == "rna" || option[ out::file::residue_type_set ]() == "rna" ) {
246  } else {
248  }
249 
250  // Very crude & slow way to extract specific tags:
251  // Are there specific tags that are required ?
252 
253  utility::vector1< std::string > requested_tags;
254  if ( option[ in::file::tags ].user() ) {
255  requested_tags = option[ in::file::tags ]().vector();
256  }
257 
258  utility::vector1< std::string > requested_user_tags;
259  if ( option[ in::file::user_tags ].user() ) {
260  requested_user_tags = option[ in::file::user_tags ]().vector();
261  }
262 
263  // Grab silent filenames from -in:file:silent option
264  utility::vector1< FileName > input_silent_files;
265  if ( option[ in::file::silent ].active() )
266  input_silent_files = option[ in::file::silent ]();
267 
268  // Grab lists of silent filenames from -in:file:silent_list option
269  utility::vector1< FileName > list_file_names;
270  if ( option[ in::file::silent_list ].active() )
271  list_file_names = option[ in::file::silent_list ]();
272 
273  for(utility::vector1< FileName >::iterator i = list_file_names.begin(), i_end = list_file_names.end(); i != i_end; ++i) {
274  std::string filename( i->name() );
275  utility::io::izstream data( filename.c_str() );
276  if ( !data.good() ) { utility_exit_with_message( "Unable to open file: " + filename + '\n' ); }
277  std::string line;
278  while( getline(data, line) ) {
279  input_silent_files.push_back( FileName(line) );
280  }
281  data.close();
282  }
283 
284  int const nstruct_flag = option[ out::nstruct ];
285  int const nstruct = std::max( 1, nstruct_flag );
286 
287 // utility::vector1< FileName >::iterator silent_file_it = input_silent_files.begin(), silent_file_it_end = input_silent_files.end();
288 // // Loop over all the silent input files
289 // for ( ; silent_file_it != silent_file_it_end; ++silent_file_it ) {
290 
291  if( input_silent_files.size() > 1 ){
292  utility_exit_with_message( "Sorry - extracitng/reading multiple silent files is disabled.");
293  }
294 
295  std::string infile = *input_silent_files.begin();
296 
297  // Read the silent structures
299  sfd.read_file( infile );
300 
301  // Grab a prefix if it exists
302  std::string outfile = option[ out::prefix ]();
303 
304  if( input_silent_files.size() > 1 ) outfile = outfile + infile;
305 
307  BaseJobDistributorOP jobdist;
308 
309  // create joblist
310  for ( core::io::silent::SilentFileData::iterator iter = sfd.begin(), end = sfd.end(); iter != end; ++iter ) {
311  if( RG.uniform() < thinout_factor ){
312  //std::cout << "Thinout: Skipping " << iter->decoy_tag() << std::endl;
313  continue; // ignore structures if thinout is required!
314  }
315 
316  // if the user requested specific tags then check for them
317  if ( option[ in::file::tags ].user() ) {
318  // Attempt to find the tag in the requested tag list
319  bool foundtag = false;
320  utility::vector1< std::string >::iterator it = requested_tags.begin(), end = requested_tags.end();
321  for ( ; it != end; ++it ) {
322  if( iter->decoy_tag() == (*it) ){
323  foundtag = true; break;
324  }
325  }
326  if( foundtag ) requested_tags.erase( it );
327  if( !foundtag ) continue; // skip this structure if none of the tags match
328  }
329 
330  // if the user requested specific tags then check for them
331  if ( option[ in::file::user_tags ].user() ) {
332  // Attempt to find the user_tag in the requested user_tag list
333  bool founduser_tag = false;
334  utility::vector1< std::string >::iterator it = requested_user_tags.begin(), end = requested_user_tags.end();
335  std::cout << iter->get_comment("user_tag") << std::endl;
336  for ( ; it != end; ++it ) {
337  if( iter->get_comment("user_tag") == (*it) ){
338  std::cerr << "FOUND: " << iter->get_comment("user_tag") << std::endl;
339  founduser_tag = true; break;
340  }
341  }
342  if( !founduser_tag ) continue; // skip this structure if none of the user_tags match
343  }
344 
345  BasicJobOP job = new BasicJob( iter->decoy_tag() , "", nstruct);
346  job->set_preserve_whole_input_tag( true );
347  input_jobs.push_back( job );
348  }
349 
350  bool const silent_output = option[ out::file::silent ].user();
351  if ( silent_output ) {
352  #ifdef BOINC
353  std::cerr << "Silent Output Mode " << std::endl;
354  #endif
355  TR << "Silent Output Mode " << std::endl;
356  jobdist = new PlainSilentFileJobDistributor(input_jobs);
357  } else {
358  #ifdef BOINC
359  std::cerr << "PDB Output Mode " << std::endl;
360  #endif
361  TR << "PDB Output Mode " << std::endl;
362  jobdist = new PlainPdbJobDistributor(input_jobs, "none");
363  }
364  if( option[ out::nooutput ]() ){
365  jobdist->disable_output();
366  jobdist->enable_ignorefinished();
367  }
368 
369 
370 
373 
374  BasicJobOP curr_job, prev_job;
375  int curr_nstruct, num_structures_processed = 0;
376  #ifdef BOINC
377  std::cerr << "Jobdist startup.." << std::endl;
378  #endif
379  jobdist->startup();
380  while( jobdist->next_job(curr_job, curr_nstruct) ) {
381 
382  // Now loop over each structure in that silent file
383  for ( core::io::silent::SilentFileData::iterator iter = sfd.begin(), end = sfd.end(); iter != end; ++iter ) {
384 
385  if( iter->decoy_tag() != curr_job->input_tag() ) continue;
386 
387  time_t pdb_start_time = time(NULL);
388 
389  std::string curr_job_tag = curr_job->output_tag(curr_nstruct);
390  #ifdef BOINC
391  #endif
392  std::cerr << "Starting work on structure: " << curr_job_tag << " <--- " << curr_job->input_tag() << std::endl;
393  // SilentStruct
394  core::pose::Pose input_pose;
395  iter->fill_pose( input_pose, *rsd_set );
396  setPoseExtraScores( input_pose, "silent_score", iter->get_energy( "score" ) );
397 
398  std::string user_tag( iter->get_comment( "user_tag" ) );
399  if ( user_tag == "" ) user_tag = iter->get_comment( "user_ta" );
400  if ( user_tag == "" ) user_tag = iter->get_comment( "user_t" );
401 
402  std::string alignment_id( iter->get_comment( "alignment_id" ) );
403 
404  std::cout << "USERTAGS: " << alignment_id << " " << user_tag << std::endl;
405 
406  // are we a centroid scoring function but the input is fullatom ? )
407  if (( (option[ OptionKeys::score::weights ]() == "score0") ||
408  (option[ OptionKeys::score::weights ]() == "score2") ||
409  (option[ OptionKeys::score::weights ]() == "score3") ||
410  (option[ OptionKeys::score::weights ]() == "score5") ||
411  (option[ OptionKeys::score::weights ]() == "score_membrane"))
412  && ( input_pose.is_fullatom() ) ) {
413  std::cout << "switching to centroid" << std::endl;
415  }
416 
417  // are we a centroid scoring function but the input is fullatom ? )
418 // if (( (option[ OptionKeys::score::weights ]() == "score12") ||
419 // (option[ OptionKeys::score::weights ]() == "standard") )
420 // && ( !input_pose.is_fullatom() ) ) {
421 // std::cout << "switching to fullatom" << std::endl;
422 // core::util::switch_to_residue_type_set( input_pose, core::chemical::STAMDARD );
423 // }
424 
425 
426 
427  // Work out the tag. If we are processing more than one silent file, add the file name too!
428  std::string tag = iter->decoy_tag();
429 
430  mover.set_current_tag( tag );
431  TR << "Working on: " << tag << std::endl;
432 
433  core::pose::PoseOP the_pose = new core::pose::Pose( input_pose );
434  if( the_pose->is_fullatom() ) core::scoring::constraints::add_fa_constraints_from_cmdline_to_pose( *the_pose );
436  the_pose->data().set(core::pose::datacache::CacheableDataType::JOBDIST_OUTPUT_TAG, new CacheableString(curr_job->output_tag(curr_nstruct)));
437 
438  // Membrane protein specific scoring - only centroid score function here:
439  if ( option[ OptionKeys::score::weights ]() == "score_membrane" && option[in::file::spanfile].user() && option[ in::file::centroid_input ].user() ) {
440  std::string const spanfile = option[ in::file::spanfile ]();
442  the_pose->data().set( core::pose::datacache::CacheableDataType::MEMBRANE_TOPOLOGY, topologyOP );
444  topology.initialize(spanfile);
445  }
446 
447 #ifdef BOINC_GRAPHICS
448  // attach boinc graphics pose observer
449  protocols::boinc::Boinc::attach_graphics_current_pose_observer( *the_pose );
450 #endif
451 
452  //////////////////////////////////////////////////////////////////////////////////////
453  //// Maybe idealize the structure before relax ?
454  if ( option[ OptionKeys::run::idealize_before_protocol ].user() ) {
456  idealizer.fast( false );
457  idealizer.apply( *the_pose );
458  }
459 
460  // run the mover !!!!
461  for(int repeat = 0; repeat < int(option[ run::repeat ]()); ++repeat ){
462  mover.apply( *the_pose );
463  }
464 
465  // Statistics
466  core::pose::setPoseExtraScores( *the_pose, "irms", core::scoring::CA_rmsd( input_pose, *the_pose ) );
467  if ( option[ in::file::native ].user() ){
468  core::pose::setPoseExtraScores( *the_pose, "rms", core::scoring::native_CA_rmsd( native_pose, *the_pose ) );
469  core::pose::setPoseExtraScores( *the_pose, "srms", core::scoring::native_CA_rmsd( native_pose, input_pose ) );
470  }
471 
472  if( ! option[ out::nooutput ]() ){
473  // for now, output pdbs
474  if (!silent_output) {
475  jobdist->dump_pose_and_map( curr_job_tag, *the_pose ); // output PDB
476  } else {
478  dynamic_cast< PlainSilentFileJobDistributor * > (jobdist());
480  //if (option[ out::file::binary_silentfile ].user()) {
481  // pss = new core::io::silent::BinaryProteinSilentStruct;
482  //} else {
483  // pss = new core::io::silent::ProteinSilentStruct;
484  //}
486  pss->fill_struct( *the_pose, curr_job_tag );
487  // run PoseEvaluators
488  evaluator->apply( *the_pose, curr_job_tag, *pss );
489  if ( user_tag != "" ) pss->add_string_value("user_tag", user_tag );
490  if ( alignment_id != "" ) pss->add_string_value("alignment_id", alignment_id );
491  jd->dump_silent( curr_nstruct, *pss );
492  }
493  }
494 
495  // output scorefile if specified or not in silent output mode
496  if ( option[ out::file::scorefile ].user() || !silent_output ) {
498  ss->fill_struct( *the_pose );
499  // run PoseEvaluators
500  evaluator->apply( *the_pose, curr_job_tag, *ss );
501  if ( user_tag != "" ) ss->add_string_value("user_tag", user_tag );
502  if ( alignment_id != "" ) ss->add_string_value("alignment_id", alignment_id );
503 
505  sfd_out.write_silent_struct( *ss, option[ out::file::scorefile ]() );
506  }
507 
508  prev_job = curr_job; // pointer assignment, not a copy op
509  num_structures_processed += 1;
510  time_t pdb_end_time = time(NULL);
511  TR << "Finished " << curr_job_tag << " in " << (long)(pdb_end_time - pdb_start_time) << " seconds." << std::endl;
512 
513  } // iterate over silent structures from a silent-file
514  }
515  jobdist->shutdown();
516 
517  // Announce any un-found tags !!
518  for ( utility::vector1< std::string >::const_iterator it = requested_tags.begin(),
519  end = requested_tags.end(); it != end; ++it ) {
520  std::cerr << "WARNING: Cannot find tag: " << (*it) << std::endl;
521  }
522 
523  } // SILENT done
524 
525  /// -------------------------- PDB ----------------------------------------------
526  if( option[ in::file::s ].user() || option[ in::file::l ].user() ){
527 
528  // are we reading PDBs ?
529  time_t overall_start_time = time(NULL);
531 
532  BaseJobDistributorOP jobdist;
533 
534  // pick the job distributor type based on a flag
535  using basic::options::option;
536  using namespace basic::options::OptionKeys;
537 
538  bool const silent_output = option[ out::file::silent ].user();
539  if ( silent_output ) {
540  TR << "Silent Output Mode " << std::endl;
541  jobdist = new PlainSilentFileJobDistributor(input_jobs);
542  } else {
543  TR << "PDB Output Mode " << std::endl;
544  jobdist = new PlainPdbJobDistributor(input_jobs, "none");
545  }
546 
547  if( option[ out::nooutput ]() ){
548  jobdist->disable_output();
549  jobdist->enable_ignorefinished();
550  }
551 
552  BasicJobOP curr_job, prev_job;
553  int curr_nstruct, num_structures_processed = 0;
554  core::pose::PoseOP input_pose; // starts NULL, coords *never* modified!
555  jobdist->startup();
556  while( jobdist->next_job(curr_job, curr_nstruct) ) {
557 
558  if( RG.uniform() < thinout_factor ){
559  //std::cout << "Thinout: Skipping " << curr_job->output_tag(curr_nstruct) << std::endl;
560  continue; // ignore structures if thinout is required!
561  }
562 
563  /// Load in input pose.
564  if ( utility::file::file_exists( curr_job->native_tag() ) ) {
565 
566  if ( option[ in::file::centroid_input ].user() ) {
567  core::import_pose::centroid_pose_from_pdb( native_pose, curr_job->native_tag() );
568  } else {
569  core::import_pose::pose_from_pdb( native_pose, curr_job->native_tag() );
570  }
571  // Set the native pose into the mover
572  mover.set_native_pose( new core::pose::Pose(native_pose) );
573 #ifdef BOINC_GRAPHICS
574  // set native for graphics
575  boinc::Boinc::set_graphics_native_pose( native_pose );
576 #endif
577  }
578 
579  std::string curr_job_tag = curr_job->output_tag(curr_nstruct);
580  mover.set_current_tag( curr_job_tag );
581  time_t pdb_start_time = time(NULL);
582  //std::cerr << "Starting work on PDB structure: " << curr_job_tag << " <--- " << curr_job->input_tag() << std::endl;
583  TR << "Starting " << curr_job->output_tag(curr_nstruct) << " ..." << std::endl;
584 
585  // we read each PDB just once to save on disk I/O
586  if( curr_job.get() != prev_job.get() || input_pose.get() == NULL ) {
587  input_pose = new core::pose::Pose();
588  if ( option[ in::file::centroid_input ].user() ) {
589  core::import_pose::centroid_pose_from_pdb( *input_pose, curr_job->input_tag() );
590  } else {
591  core::import_pose::pose_from_pdb( *input_pose, curr_job->input_tag() );
592  }
593  }
594 
595  if( input_pose->total_residue() == 0 ){
596  utility_exit_with_message( "Unable to read PDB file: " + curr_job->input_tag() + '\n' );
597  }
598 
599  // Make a modifiable copy of the pose read from disk
600  core::pose::PoseOP the_pose = new core::pose::Pose( *input_pose );
601  if( the_pose->is_fullatom() ) core::scoring::constraints::add_fa_constraints_from_cmdline_to_pose( *the_pose );
603 
604  the_pose->data().set(core::pose::datacache::CacheableDataType::JOBDIST_OUTPUT_TAG, new CacheableString(curr_job->output_tag(curr_nstruct)));
605 
606  // Membrane protein specific scoring - only centroid score function here:
607  if ( option[ OptionKeys::score::weights ]() == "score_membrane" && option[in::file::spanfile].user() && option[ in::file::centroid_input ].user() ) {
608  std::string const spanfile = option[ in::file::spanfile ]();
610  the_pose->data().set( core::pose::datacache::CacheableDataType::MEMBRANE_TOPOLOGY, topologyOP );
612  topology.initialize(spanfile);
613  }
614 
615 #ifdef BOINC_GRAPHICS
616  // attach boinc graphics pose observer
617  protocols::boinc::Boinc::attach_graphics_current_pose_observer( *the_pose );
618 #endif
619  //////////////////////////////////////////////////////////////////////////////////////
620  //// Maybe idealize the structure before relax ?
621  if ( option[ OptionKeys::run::idealize_before_protocol ].user() ) {
623  idealizer.fast( false );
624  idealizer.apply( *the_pose );
625  }
626 
627  for(int repeat = 0; repeat < int(option[ run::repeat ]()); ++repeat ){
628  mover.apply( *the_pose );
629  }
630 
631  // Statistics
632  core::pose::setPoseExtraScores( *the_pose, "irms", core::scoring::CA_rmsd( *input_pose, *the_pose ) );
633  if ( option[ in::file::native ].user() )
634  core::pose::setPoseExtraScores( *the_pose, "rms", core::scoring::native_CA_rmsd( native_pose, *the_pose ) );
635 
636  // for now, output pdbs
637  if (!silent_output) {
638  jobdist->dump_pose_and_map( curr_job_tag, *the_pose ); // output PDB
639  } else {
641  dynamic_cast< PlainSilentFileJobDistributor * > (jobdist());
643  //if (option[ out::file::binary_silentfile ].user()) {
644  // pss = new core::io::silent::BinaryProteinSilentStruct;
645  //} else {
646  // pss = new core::io::silent::ProteinSilentStruct;
647  //}
649  pss->fill_struct( *the_pose, curr_job_tag );
650  jd->dump_silent( curr_nstruct, *pss );
651  }
652  // output scorefile if specified or not in silent output mode
653  if ( option[ out::file::scorefile ].user() || !silent_output ) {
655  ss->fill_struct( *the_pose );
657  sfd_out.write_silent_struct( *ss, option[ out::file::scorefile ]() );
658  }
659 
660  prev_job = curr_job; // pointer assignment, not a copy op
661  num_structures_processed += 1;
662  time_t pdb_end_time = time(NULL);
663  TR << "Finished " << curr_job->output_tag(curr_nstruct) << " in " << (long)(pdb_end_time - pdb_start_time) << " seconds." << std::endl;
664  } // loop over jobs and nstructs
665  jobdist->shutdown();
666 
667  time_t overall_end_time = time(NULL);
668  TR << "Finished all " << num_structures_processed << " structures in " << (long)(overall_end_time - overall_start_time) << " seconds." << std::endl;
669  if ( num_structures_processed == 0 )
670  basic::Warning() << "No structures processed. Existing output files may have been skipped, did you mean to delete them or to use the -overwrite flag?" << std::endl;
671  return 0;
672  } // PDB done
673 
674  return 0;
675 } // universal_main
676 
677 ////////////////////////////////////////////////////////////////////////////////////////////////
678 ///@details Example of how to use the job distributor that will write
679 /// either a pdb or a raw_data (silent) file depending on an input flag
680 /// Because PDBs are so big and inefficient, this function is NOT RECOMMENDED
681 /// for use in production environements.
682 /// If this function doesn't meet your needs as is, please COPY it into your own main method
683 /// rather than modifying it in place!
684 /// The goal is to keep this one as a simple-as-possible EXAMPLE for others,
685 /// although it will suffice for many protocols as-is.
687  protocols::moves::Mover & mover,
688  bool random_permutation
689 )
690 {
691  //using core::pose::datacache::CacheableDataType::JOBDIST_OUTPUT_TAG;
692  using basic::datacache::CacheableString;
693 
694  time_t overall_start_time = time(NULL);
696 
697 #ifndef USEMPI
698  // Reduce read contention between processes by randomizing the order in which structures are processed
699  // Do not randomize, though, if job distribution is controlled by MPI
700  if( random_permutation ) {
701  numeric::random::random_permutation( input_jobs, numeric::random::RG );
702  }
703 #endif
704 
705  BasicJobOP curr_job, prev_job;
706  int curr_nstruct, num_structures_processed = 0;
707  core::pose::PoseOP input_pose; // starts NULL, coords *never* modified!
708  core::pose::PoseOP native_pose; // starts NULL, coords *never* modified!
709 
710  BaseJobDistributorOP jobdist;
711 
712  // pick the job distributor type based on a flag
713  using basic::options::option;
714  using namespace basic::options::OptionKeys;
715 
716  // What on earth is "raw" ? Surely these are called silent files ?
717  bool const is_raw = option[ out::file::raw ]();
718  bool const silent_output = option[ out::file::silent ].user();
719  if ( is_raw || silent_output ) {
720  jobdist = new PlainRawJobDistributor(input_jobs, ".out");
721  } else {
722  jobdist = new PlainPdbJobDistributor(input_jobs, "score");
723  }
724 
725  if( option[ out::nooutput ]() ){
726  jobdist->disable_output();
727  jobdist->enable_ignorefinished();
728  }
729 
730  std::map < std::string, core::Real > score_map;
731 
732  jobdist->startup();
733  while( jobdist->next_job(curr_job, curr_nstruct) ) {
734  time_t pdb_start_time = time(NULL);
735  TR << "Starting " << curr_job->output_tag(curr_nstruct) << " ..." << std::endl;
736  jobdist->temp_file( curr_job->output_tag(curr_nstruct) );
737 
738  // we read each PDB just once to save on disk I/O
739  if( curr_job.get() != prev_job.get() || input_pose.get() == NULL ) {
740  input_pose = new core::pose::Pose();
741  if ( option[ in::file::centroid_input ].user() ) {
742  core::import_pose::centroid_pose_from_pdb( *input_pose, curr_job->input_tag() );
743  native_pose = new core::pose::Pose();
744  core::import_pose::centroid_pose_from_pdb( *native_pose, curr_job->native_tag() );
745  } else {
746  core::import_pose::pose_from_pdb( *input_pose, curr_job->input_tag() );
747  native_pose = new core::pose::Pose();
748  core::import_pose::pose_from_pdb( *native_pose, curr_job->native_tag() );
749  }
750  }
751  mover.set_input_pose( input_pose );
752  mover.set_native_pose( native_pose );
753 
754  // Make a modifiable copy of the pose read from disk
755  core::pose::PoseOP the_pose = new core::pose::Pose( *input_pose );
756  the_pose->data().set(core::pose::datacache::CacheableDataType::JOBDIST_OUTPUT_TAG, new CacheableString(curr_job->output_tag(curr_nstruct)));
757 
758  mover.apply( *the_pose );
759 
760  prev_job = curr_job; // pointer assignment, not a copy op
761  num_structures_processed += 1;
762  time_t pdb_end_time = time(NULL);
763  TR << "Finished " << curr_job->output_tag(curr_nstruct) << " in " << (long)(pdb_end_time - pdb_start_time) << " seconds." << std::endl;
764 
765  score_map = get_score_map( *the_pose );
766 
767  if ( option[ run::timer ].user() ){
768  score_map["time"] = pdb_end_time - pdb_start_time;
769  }
770 
771  jobdist->score_map( score_map );
772  jobdist->dump_pose_and_map( curr_job->output_tag(curr_nstruct), *the_pose );
773 
774  } // loop over jobs and nstructs
775  jobdist->shutdown();
776 
777  time_t overall_end_time = time(NULL);
778  TR << "Finished all " << num_structures_processed << " structures in " << (long)(overall_end_time - overall_start_time) << " seconds." << std::endl;
779  if ( num_structures_processed == 0 )
780  basic::Warning() << "No structures processed. Existing output files may have been skipped, did you mean to delete them?" << std::endl;
781  return 0;
782 }
783 ////////////////////////////////////////////////////////////////////////////////////////////////
784 ///@details Example of how to use the job distributor with plain old PDB files.
785 /// Because PDBs are so big and inefficient, this function is NOT RECOMMENDED
786 /// for use in production environements.
787 /// If this function doesn't meet your needs as is, please COPY it into your own main method
788 /// rather than modifying it in place!
789 /// The goal is to keep this one as a simple-as-possible EXAMPLE for others,
790 /// although it will suffice for many protocols as-is.
792  protocols::moves::Mover & mover,
794 )
795 {
796  //using core::pose::datacache::CacheableDataType::JOBDIST_OUTPUT_TAG;
797  using basic::datacache::CacheableString;
798 
799  time_t overall_start_time = time(NULL);
801 
802 #ifndef USEMPI
803  // Reduce read contention between processes by randomizing the order in which structures are processed
804  // Do not randomize, though, if job distribution is controlled by MPI
805  numeric::random::random_permutation( input_jobs, numeric::random::RG );
806 #endif
807 
808  BaseJobDistributorOP jobdist;
809 
810  // pick the job distributor type based on a flag
811  using basic::options::option;
812  using namespace basic::options::OptionKeys;
813 
814  bool const silent_output = option[ out::file::silent ].user();
815  if ( silent_output ) {
816  TR << "Silent Output Mode " << std::endl;
817  jobdist = new PlainSilentFileJobDistributor(input_jobs);
818  } else {
819  TR << "PDB Output Mode " << std::endl;
820  jobdist = new PlainPdbJobDistributor(input_jobs, "score");
821  }
822 
823  if( option[ out::nooutput ]() ){
824  jobdist->disable_output();
825  jobdist->enable_ignorefinished();
826  }
827 
828  // load native pose (if provided)
829  core::pose::Pose native_pose;
830  if ( option[ in::file::native ].user() ) {
831  core::import_pose::pose_from_pdb( native_pose, option[ in::file::native ]() );
832  }
833 
834  BasicJobOP curr_job, prev_job;
835  int curr_nstruct, num_structures_processed = 0;
836  core::pose::PoseOP input_pose; // starts NULL, coords *never* modified!
837  jobdist->startup();
838  while( jobdist->next_job(curr_job, curr_nstruct) ) {
839  time_t pdb_start_time = time(NULL);
840  TR << "Starting " << curr_job->output_tag(curr_nstruct) << " ..." << std::endl;
841 
842  // we read each PDB just once to save on disk I/O
843  if( curr_job.get() != prev_job.get() || input_pose.get() == NULL ) {
844  input_pose = new core::pose::Pose();
845  if ( option[ in::file::centroid_input ].user() ) {
846  core::import_pose::centroid_pose_from_pdb( *input_pose, curr_job->input_tag() );
847  } else {
848  core::import_pose::pose_from_pdb( *input_pose, curr_job->input_tag() );
849  }
850  }
851 
852  // Make a modifiable copy of the pose read from disk
853  core::pose::PoseOP the_pose = new core::pose::Pose( *input_pose );
854  the_pose->data().set(core::pose::datacache::CacheableDataType::JOBDIST_OUTPUT_TAG, new CacheableString(curr_job->output_tag(curr_nstruct)));
855 
856  for(int repeat = 0; repeat < int(option[ run::repeat ]()); ++repeat ){
857  mover.apply( *the_pose );
858  }
859 
860  // Score new structure. Cached energies (including *residue* energies)
861  // must be up-to-date in order to get sensible output. If you remove these
862  // lines, you *must* insert equivalent logic at the end of all apply() methods
863  // (or at least for all movers that might be passed to this function).
864  (*scorefxn)( *the_pose );
865  /// Now handled automatically. scorefxn->accumulate_residue_total_energies( *the_pose );
866 
867  // Statistics
868  core::pose::setPoseExtraScores( *the_pose, "irms", core::scoring::CA_rmsd( *input_pose, *the_pose ) );
869 
870  if ( option[ in::file::native ].user() )
871  core::pose::setPoseExtraScores( *the_pose, "rms", core::scoring::native_CA_rmsd( native_pose, *the_pose ) );
872 
873  // for now, output pdbs
874  if (!silent_output) {
875  jobdist->dump_pose_and_map( curr_job->output_tag(curr_nstruct), *the_pose ); // output PDB
876  } else {
878  dynamic_cast< protocols::jobdist::PlainSilentFileJobDistributor * > (jobdist());
880  pss.fill_struct( *the_pose, curr_job->output_tag(curr_nstruct) );
881  jd->dump_silent( curr_nstruct, pss );
882  }
883 
884  prev_job = curr_job; // pointer assignment, not a copy op
885  num_structures_processed += 1;
886  time_t pdb_end_time = time(NULL);
887  TR << "Finished " << curr_job->output_tag(curr_nstruct) << " in " << (long)(pdb_end_time - pdb_start_time) << " seconds." << std::endl;
888  } // loop over jobs and nstructs
889  jobdist->shutdown();
890 
891  time_t overall_end_time = time(NULL);
892  TR << "Finished all " << num_structures_processed << " structures in " << (long)(overall_end_time - overall_start_time) << " seconds." << std::endl;
893  if ( num_structures_processed == 0 )
894  basic::Warning() << "No structures processed. Existing output files may have been skipped, did you mean to delete them or to use the -overwrite flag?" << std::endl;
895  return 0;
896 }
897 
898 ////////////////////////////////////////////////////////////////////////////////////////////////
899 ///@details Example of how to use the job distributor with silent files.
900 /// If this function doesn't meet your needs as is, please COPY it into your own main method
901 /// rather than modifying it in place!
902 /// The goal is to keep this one as a simple-as-possible EXAMPLE for others,
903 /// although it will suffice for many protocols as-is.
905  protocols::moves::Mover & mover,
907 )
908 {
909  //using core::pose::datacache::CacheableDataType::JOBDIST_OUTPUT_TAG;
910  using basic::datacache::CacheableString;
911 
912  time_t overall_start_time = time(NULL);
914  // Reduce read contention between processes by randomizing the order in which structures are processed
915  numeric::random::random_permutation( input_jobs, numeric::random::RG );
916  AtomTreeDiffJobDistributor jobdist( input_jobs, "silent.out" );
917 
918  BasicJobOP curr_job, prev_job;
919  int curr_nstruct, num_structures_processed = 0;
920  core::pose::PoseOP input_pose; // starts NULL, coords *never* modified!
921  jobdist.startup();
922  while( jobdist.next_job(curr_job, curr_nstruct) ) {
923  time_t pdb_start_time = time(NULL);
924  TR << "Starting " << curr_job->output_tag(curr_nstruct) << " ..." << std::endl;
925 
926  // we read each PDB just once to save on disk I/O
927  if( curr_job.get() != prev_job.get() || input_pose.get() == NULL ) {
928  input_pose = new core::pose::Pose();
929  core::import_pose::pose_from_pdb( *input_pose, curr_job->input_tag() );
930  }
931 
932  // Make a modifiable copy of the pose read from disk
933  core::pose::PoseOP the_pose = new core::pose::Pose( *input_pose );
934  the_pose->data().set(core::pose::datacache::CacheableDataType::JOBDIST_OUTPUT_TAG, new CacheableString(curr_job->output_tag(curr_nstruct)));
935  mover.apply( *the_pose );
936 
937  // Score new structure and add to silent file
938  std::map< std::string, core::Real > scores;
940  jobdist.dump_pose( curr_job->output_tag(curr_nstruct), scores, *input_pose, *the_pose );
941 
942  prev_job = curr_job; // pointer assignment, not a copy op
943  num_structures_processed += 1;
944  time_t pdb_end_time = time(NULL);
945  TR << "Finished " << curr_job->output_tag(curr_nstruct) << " in " << (long)(pdb_end_time - pdb_start_time) << " seconds." << std::endl;
946  } // loop over jobs and nstructs
947  jobdist.shutdown();
948 
949  time_t overall_end_time = time(NULL);
950  TR << "Finished all " << num_structures_processed << " structures in " << (long)(overall_end_time - overall_start_time) << " seconds." << std::endl;
951  if ( num_structures_processed == 0 )
952  basic::Warning() << "No structures processed. Existing output files may have been skipped, did you mean to delete them or use the -overwrite flag?" << std::endl;
953  return 0;
954 }
955 ////////////////////////////////////////////////////////////////////////////////////////////////
956 } // namespace jobdist
957 } // namespace protocols