31 #include <basic/options/option.hh>
32 #include <basic/options/keys/packing.OptionKeys.gen.hh>
36 #include <basic/Tracer.hh>
39 #include <utility/exit.hh>
40 #include <utility/string_util.hh>
41 #include <utility/LexicographicalIterator.hh>
44 #include <utility/vector1.hh>
54 static basic::Tracer
TR(
"protocols.match.upstream.ProteinUpstreamBuilder" );
75 n_samples_wi_sd_range_( 0 ),
76 nrchi_prob_minimum_for_extra_samples_( 0.2 ),
77 n_samples_per_side_of_nrchi_bin_( 0 )
214 Size const n_atoms = res.natoms();
216 controlling_chi_for_atom_ = res.last_controlling_chi();
217 which_point_for_atom_.resize( n_atoms );
218 std::fill( which_point_for_atom_.begin(), which_point_for_atom_.end(), 0 );
221 Size const n_chi = res.nchi();
223 chitip_atoms_.resize( n_chi );
224 std::fill( chitip_atoms_.begin(), chitip_atoms_.end(), 0 );
226 ht_for_chitip_atoms_.resize( n_chi );
227 for ( Size ii = 1; ii <= n_chi; ++ii ) ht_for_chitip_atoms_[ ii ].set_identity();
229 nonchitip_atoms_.resize( res.nchi() );
230 for ( Size ii = 1; ii <= n_chi; ++ii ) nonchitip_atoms_[ ii ].clear();
232 points_for_nonchitip_atoms_.resize( res.nchi() );
233 for ( Size ii = 1; ii <= n_chi; ++ii ) points_for_nonchitip_atoms_[ ii ].clear();
235 if ( nchi() == 0 ) return; // match from gly? can't see why you'd want to!
238 for ( Size ii = 1; ii <= n_chi; ++ii ) {
239 assert( res.chi_atoms( ii ).size() == 4 );
242 chiat2( res.chi_atoms( ii )[ 2 ] ),
243 chiat3( res.chi_atoms( ii )[ 3 ] ),
244 chiat4( res.chi_atoms( ii )[ 4 ] );
246 chitip_atoms_[ ii ] = chiat4;
249 ht_for_chitip_atoms_[ ii ].set_xaxis_rotation_rad( -1 * res.icoor( chiat4 ).theta() );
250 ht_for_chitip_atoms_[ ii ].walk_along_z( res.icoor( chiat4 ).d() );
252 HTReal chi_tip_frame(
257 Size const n_nontip_ats_for_chi = res.atoms_last_controlled_by_chi( ii ).size() - 1;
259 nonchitip_atoms_[ ii ].reserve( n_nontip_ats_for_chi );
260 points_for_nonchitip_atoms_[ ii ].reserve( n_nontip_ats_for_chi );
262 for ( Size jj = 1; jj <= res.atoms_last_controlled_by_chi( ii ).size(); ++jj ) {
263 Size const jjatom = res.atoms_last_controlled_by_chi( ii )[ jj ];
264 if ( jjatom == chiat4 ) continue;
266 Vector jjloc_in_chitip_frame = chi_tip_frame.to_local_coordinate( res.xyz( jjatom ) );
267 nonchitip_atoms_[ ii ].push_back( jjatom );
268 points_for_nonchitip_atoms_[ ii ].push_back( jjloc_in_chitip_frame );
269 which_point_for_atom_[ jjatom ] = points_for_nonchitip_atoms_[ ii ].size();
276 backbone_only_( false ),
277 rot_prob_accumulation_limit_( 0.98 ),
278 check_fa_dun_(false),
292 if (
this != &rhs ) {
329 if (
restype_->atom_is_backbone( ii )) {
332 Size min_path_dist = 6;
334 if (
restype_->atom_is_backbone( jj ) && (
Size)
restype_->path_distance( ii, jj ) < min_path_dist ) {
335 min_path_dist =
restype_->path_distance( ii, jj );
379 num_chi_samples_total_( 1 )
393 for (
Size ii = 1; ii <= nchi; ++ii ) {
395 if ( ii > sample.
nchi() ) {
435 utility_exit_with_message(
"unimplemented rotamer building strategy" );
449 using namespace core::pack::task;
460 }
else if ( extra_proton_chi ) {
473 if ( extra_proton_chi ) {
480 if ( extra_proton_chi ) {
492 utility_exit_with_message(
"Unrecognized chi type in ProteinUpstreamBuilder for " +
493 build_set.
restype().
name() +
" chi# " + utility::to_string( chi ) );
504 using namespace core::pack::task;
528 switch ( behavior ) {
630 utility_exit_with_message(
"Requested ex sample level not yet supported" );
647 runtime_assert( stratdat.
sd_range() > 0 );
648 runtime_assert( stratdat.
step_size() > 0 );
650 nsamps = 1 + 2 * nsteps;
655 for (
Size ii = nsteps; ii >= 1; --ii ) {
659 for (
Size ii = 1; ii <= nsteps; ++ii ) {
687 chi_samples_[ chi ].push_back( lower_edge + ii * step );
709 utility_exit_with_message(
"Cannot treat chi " + utility::to_string( chi ) +
" as non-rotameric; did you forget the -dun10 flag?" );
721 frames_[ chi ].resize( nsamples );
722 for (
Size ii = 1; ii <= nsamples; ++ii ) {
731 using namespace basic::options;
732 using namespace basic::options::OptionKeys::packing;
733 using namespace core::pack::task;
740 if ( option[ ex1::level ].user() && option[ ex1::level ] > sample_level ) sample_level =
ExtraRotSample( option[ ex1::level ]() );
744 if ( option[ ex2::level ].user() && option[ ex2::level ] > sample_level ) sample_level =
ExtraRotSample( option[ ex2::level ]() );
748 if ( option[ ex3::level ].user() && option[ ex3::level ] > sample_level ) sample_level =
ExtraRotSample( option[ ex3::level ]() );
752 if ( option[ ex4::level ].user() && option[ ex4::level ] > sample_level ) sample_level =
ExtraRotSample( option[ ex4::level ]() );
805 using namespace utility;
807 std::list< Hit > local_hit_list;
809 Size upstream_state = 1;
810 Size n_possible_hits = 0;
817 bool check_fa_dun(
build_sets_[ii].check_fa_dun() );
821 static_cast< ProteinBackboneBuildPoint const & >
831 Real accumulated_probability( 0.0 );
841 ii, rescoords,
build_sets_[ ii ].restype_geometry().CB_atom_id() );
844 Size ii_nrotamers( 0 );
846 for (
Size jj = 1; jj <= rotamer_samples.size(); ++jj ) {
855 build_sets_[ ii ], rotamer_samples[ jj ], avoid_building_any_rotamers );
865 utility::LexicographicalIterator lex( additional_chi_samples.
n_samples_per_chi() );
869 Size n_chi_needing_update = ii_nchi;
870 while ( ! lex.at_end() ) {
871 assert( ( n_chi_needing_update >= 1 || ii_nchi == 0 ) && n_chi_needing_update <= ii_nchi );
876 bool rotamer_acceptable(
true );
882 for (
Size kk = ii_nchi - n_chi_needing_update + 1; kk <= ii_nchi; ++kk ) {
883 chitip_frames[ kk ] = chitip_frames[ kk - 1 ] *
884 additional_chi_samples.
frame( kk, lex[ kk ] ) *
887 rescoords.
chi()[ kk ] = additional_chi_samples.
chi_sample( kk, lex[ kk ] );
889 rotamer_acceptable =
false;
891 if ( rotamer_acceptable ) {
899 rotamer_acceptable =
false;
910 if ( kk == ii_nchi && rotamer_acceptable && check_fa_dun ) {
911 for (
core::Size res_chi(1); res_chi<= ii_nchi; ++res_chi) {
912 rescoords.
chi()[res_chi] = additional_chi_samples.
chi_sample( res_chi, lex[ res_chi ] );
914 if( rotlib->rotamer_energy( rescoords, dunscratch ) >= fa_dun_cutoff ){
915 rotamer_acceptable =
false;
919 if ( ! rotamer_acceptable ) {
928 for (
Size ll = kk+1; ll <= ii_nchi; ++ll ) {
929 n_skipped *= lex.dimsize( ll );
931 upstream_state += n_skipped;
932 ii_nrotamers += n_skipped;
933 n_chi_needing_update = lex.continue_at_dimension( kk );
937 if ( ! rotamer_acceptable )
continue;
944 std::list< Hit > hits =
build_sets_[ ii ].algorithm().build(
948 local_hit_list.splice( local_hit_list.end(), hits );
953 n_chi_needing_update = ++lex;
964 accumulated_probability += rotamer_samples[ jj ].probability();
965 if ( accumulated_probability >
build_sets_[ ii ].probability_limit() )
break;
976 if ( orig && & (orig->input_conformation().type()) == & (
build_sets_[ ii ].
restype()) ) {
978 std::list< Hit > hits =
build_sets_[ ii ].algorithm().build(
981 orig->input_conformation() );
982 local_hit_list.splice( local_hit_list.end(), hits );
984 n_possible_hits +=
build_sets_[ ii ].algorithm().n_possible_hits_per_upstream_conformation();
991 n_possible_hits += ii_nrotamers *
build_sets_[ ii ].algorithm().n_possible_hits_per_upstream_conformation();
995 assert( dynamic_cast< ProteinBackboneBuildPoint const * > ( & build_point ) );
999 TR <<
"Considered " << n_possible_hits <<
" downstream conformations at residue " << bb.
original_insertion_point() <<
" and found " << local_hit_list.size() <<
" hits." << std::endl;
1001 return local_hit_list;
1018 std::list< Hit > hitlist;
1019 hitlist.push_back( hit );
1020 recover_hits( hitlist.begin(), hitlist.end(), build_point, processor );
1025 std::list< Hit >::const_iterator hit_iter,
1026 std::list< Hit >::const_iterator hits_end,
1032 assert( hit_iter == hits_end || hit_iter->scaffold_build_id() == build_point.
index() );
1036 Size upstream_state = 1;
1039 Real accumulated_probability( 0.0 );
1044 for (
Size jj = 1; jj <= rotamer_samples.size(); ++jj ) {
1062 build_sets_[ ii ], rotamer_samples[ jj ],
false );
1066 utility::LexicographicalIterator lex( additional_chi_samples.
n_samples_per_chi() );
1073 lex.set_position_from_index( hit_iter->first()[ 2 ] - upstream_state + 1 );
1079 for (
Size kk = 1; kk <= ii_nchi; ++kk ) {
1080 chitip_frames[ kk ] = chitip_frames[ kk - 1 ] *
1081 additional_chi_samples.
frame( kk, lex[ kk ] ) *
1084 rescoords.
chi()[ kk ] = additional_chi_samples.
chi_sample( kk, lex[ kk ] );
1099 std::list< Hit >::const_iterator last_hit = hit_iter;
1101 if ( hit_iter == hits_end )
return;
1102 runtime_assert( hit_iter->scaffold_build_id() == last_hit->scaffold_build_id() );
1103 runtime_assert( hit_iter->upstream_conf_id() >= last_hit->upstream_conf_id() );
1115 accumulated_probability += rotamer_samples[ jj ].probability();
1116 if ( accumulated_probability >
build_sets_[ ii ].probability_limit() )
break;
1124 if ( orig && & (orig->input_conformation().type()) == & (
build_sets_[ ii ].
restype()) ) {
1126 if ( hit_iter->first()[ 2 ] == upstream_state ) {
1127 processor.
process_hit( *hit_iter, orig->input_conformation() );
1130 if ( hit_iter == hits_end )
return;
1138 utility_exit_with_message(
"ProteinUpstreamBuilder was unable to recover rotamer " +
1139 utility::to_string( hit_iter->first()[ 2 ] ) +
" from scaffold build position " +
1140 utility::to_string( hit_iter->first()[ 1 ] ) );
1152 return & (
build_sets_[ which_restype ].restype() );
1162 Hit const & other_hit,
1167 return other.
compatible( other_hit, build_point_other, *
this, my_hit, build_point_mine,
false );
1175 Hit const & other_hit,
1182 if ( build_point_mine.
index() != build_point_other.
index() ) {
1187 }
else if ( other_hit.
first()[ 2 ] == 1 && other_builder.
build_sets_[ 1 ].backbone_only() ) {
1227 utility_exit_with_message(
"Could not retrieve a build set for residue type " + restype->name() );
1262 if ( ! dynamic_cast< ProteinBackboneBuildPoint const * > ( & build_point ) ) {
1263 utility_exit_with_message(
"Input to ProteinUpstreamBuilder not castable to ProteinBackboneBuildPoint *" );
1291 rescoords.
set_xyz( oneHA_index,
1311 runtime_assert( CB_no != 0 );
1313 Vector halfpoint_input = 0.5 * ( build_point.
N_pos() + build_point.
C_pos() );
1314 HTReal input_frame( build_point.
N_pos(), halfpoint_input, build_point.
CA_pos() );
1333 if ( atomno == 0 )
return false;
1336 Size const MIN_CHEMBOND_SEP_FROM_CA = 4;
1337 if (
build_sets_[ build_set_id ].nbonds_from_bb_atom( atomno ) > MIN_CHEMBOND_SEP_FROM_CA ) {
1339 }
else if (
build_sets_[ build_set_id ].nbonds_from_bb_atom( atomno ) == MIN_CHEMBOND_SEP_FROM_CA ) {
1351 Size capos =
build_sets_[ build_set_id ].restype_geometry().CA_atom_id();
1354 build_sets_[ build_set_id ].atom_radius( atomno ) );
1355 Real min_d2 = min_d * min_d;
1356 if ( rescoords.
xyz( atomno ).distance_squared( rescoords.
xyz( capos )) > min_d2 ) {