00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035 #ifndef ESBTL_MOLECULAR_SYSTEM_H
00036 #define ESBTL_MOLECULAR_SYSTEM_H
00037
00038 #include <map>
00039 #include <list>
00040 #include <vector>
00041 #include <cassert>
00042 #include <string>
00043 #include <iostream>
00044 #include <boost/tuple/tuple.hpp>
00045 #include <ESBTL/iterators.h>
00046 #include <ESBTL/constants.h>
00047
00052 namespace ESBTL{
00053
00059 template <class Items,class Point>
00060 class Molecular_system{
00061 typedef Molecular_system<Items,Point> Self;
00062 public:
00063 typedef typename Items::template Model_wrapper<Molecular_system,Point>::Type Model;
00064 typedef typename Items::template Chain_wrapper<Molecular_system,Point>::Type Chain;
00065 typedef typename Items::template Atom_wrapper<Molecular_system,Point>::Type Atom;
00066 typedef typename Items::template Residue_wrapper<Molecular_system,Point>::Type Residue;
00067 typedef std::map<int,Model> Model_container;
00068
00069
00070
00071 static const Model& dereference (typename Model_container::const_iterator it) {return it->second;}
00072 static Model& dereference (typename Model_container::iterator it) {return it->second;}
00073
00075 typedef internal::Model_iterator_from_system<Self,false> Models_iterator;
00077 typedef internal::Model_iterator_from_system<Self,true> Models_const_iterator;
00078
00080 Models_iterator models_begin() {return Models_iterator(model_container_.begin()); }
00082 Models_iterator models_end() {return Models_iterator(model_container_.end()); }
00084 Models_const_iterator models_begin() const {return Models_const_iterator(model_container_.begin());}
00086 Models_const_iterator models_end() const {return Models_const_iterator(model_container_.end()); }
00087
00088
00089 Molecular_system(int index,std::string name="no_name"):name_(name),index_(index),alternate_location_(' '){}
00090
00091 template<class Line_format>
00092 void interpret_line(const Line_format& line_format,const std::string& line,int current_model){
00093 Model& model=get_or_create_model(current_model);
00094 Chain& chain=model.get_or_create_chain(line_format,line);
00095 Residue& residue=chain.get_or_create_residue(line_format,line);
00096 residue.add_atom(line_format,line);
00097 }
00098
00099 bool has_no_model() const{
00100 return model_container_.empty();
00101 }
00102
00103 bool has_model(int i) const{
00104 return model_container_.find(i)!=model_container_.end();
00105 }
00106
00107 size_t number_of_models() const {
00108 return model_container_.size();
00109 }
00110
00111 void set_altloc(char c) {alternate_location_=c;}
00112
00113
00114
00115 DECLARE_AND_ACCESS(name,std::string)
00116 DECLARE_AND_ACCESS(index,int)
00117 DECLARE_AND_ACCESS(alternate_location,char)
00118
00119
00120 Model& get_or_create_model(int i){
00121 typename Model_container::iterator itm=model_container_.find(i);
00122 if (itm==model_container_.end()){
00123 itm=model_container_.insert( std::make_pair(i,Model(i,*this)) ).first;
00124 }
00125 return itm->second;
00126 }
00127
00128 Model& get_model(int i){
00129 typename Model_container::iterator itm=model_container_.find(i);
00130 if (itm==model_container_.end()){std::cerr <<"Cannot find model " << i << std::endl; exit(EXIT_FAILURE);}
00131 return itm->second;
00132 }
00133
00134
00135 private:
00136 Model_container model_container_;
00137 };
00138
00142 template<class System_>
00143 class Molecular_model{
00144
00145 public:
00146 typedef System_ System;
00147 typedef typename System::Chain Chain;
00148 typedef std::map<char,Chain> Chain_container;
00149 private:
00150 typedef Molecular_model<System_> Self;
00151 const System& system_;
00152 Chain_container chain_container_;
00153 public:
00154 const System& system() const {return system_;}
00155
00156 Molecular_model(int nbm,const System& sys):system_(sys),model_number_(nbm){}
00157
00158 template <class Line_format>
00159 Chain& get_or_create_chain(const Line_format& line_format,const std::string& line){
00160 char ch=line_format.get_chain_identifier(line);
00161 typename Chain_container::iterator itch=chain_container_.find(ch);
00162 if (itch==chain_container_.end())
00163 itch=chain_container_.insert(std::make_pair(ch,Chain(line_format,line,*this))).first;
00164 return itch->second;
00165 }
00166
00167 Chain& get_or_create_chain(char id){
00168 typename Chain_container::iterator itch=chain_container_.find(id);
00169 if (itch==chain_container_.end())
00170 itch=chain_container_.insert(std::make_pair(id,Chain(id,*this))).first;
00171 return itch->second;
00172 }
00173
00174 const Chain& get_chain(char id) const {
00175 typename Chain_container::const_iterator itch=chain_container_.find(id);
00176 assert (itch!=chain_container_.end());
00177 return itch->second;
00178 }
00179
00180 const typename System::Residue& get_residue(char ch_id,int ressn,char insc=' ') const {
00181 return get_chain(ch_id).get_residue(ressn,insc);
00182 }
00183
00184 const typename System::Atom& get_atom(char ch_id,int ressn,char insc,unsigned atom_sn) const {
00185 return get_chain(ch_id).get_residue(ressn,insc).get_atom(atom_sn);
00186 }
00187
00188 size_t number_of_chains() const {
00189 return chain_container_.size();
00190 }
00191
00192 size_t number_of_residues() const {
00193 size_t total=0;
00194 for (typename Chain_container::const_iterator it=chain_container_.begin();it!=chain_container_.end();++it)
00195 total+=it->second.number_of_residues();
00196 return total;
00197 }
00198
00199 size_t number_of_atoms() const {
00200 size_t total=0;
00201 for (typename Chain_container::const_iterator it=chain_container_.begin();it!=chain_container_.end();++it)
00202 total+=it->second.number_of_atoms();
00203 return total;
00204 }
00205
00206
00207
00208 static const Chain& dereference (typename Chain_container::const_iterator it) {return it->second;}
00209 static Chain& dereference (typename Chain_container::iterator it) {return it->second;}
00210
00212 typedef internal::Chains_iterator_from_model<Self,true> Chains_const_iterator;
00214 typedef internal::Chains_iterator_from_model<Self,false> Chains_iterator;
00215
00217 Chains_iterator chains_begin() {return Chains_iterator(chain_container_.begin());}
00219 Chains_iterator chains_end() {return Chains_iterator(chain_container_.end());}
00220
00222 Chains_const_iterator chains_begin() const {return Chains_const_iterator(chain_container_.begin());}
00224 Chains_const_iterator chains_end() const {return Chains_const_iterator(chain_container_.end());}
00225
00227 typedef internal::Residues_iterator_from_model<Self,true> Residues_const_iterator;
00229 typedef internal::Residues_iterator_from_model<Self,false> Residues_iterator;
00230
00232 Residues_iterator residues_begin() {return Residues_iterator(*this);}
00234 Residues_iterator residues_end() {return Residues_iterator(*this,true);}
00235
00237 Residues_const_iterator residues_begin() const {return Residues_const_iterator(*this);}
00239 Residues_const_iterator residues_end() const {return Residues_const_iterator(*this,true);}
00240
00241
00243 typedef internal::Atoms_iterator_from_model<Self,true> Atoms_const_iterator;
00245 typedef internal::Atoms_iterator_from_model<Self,false> Atoms_iterator;
00246
00248 Atoms_iterator atoms_begin() {return Atoms_iterator(*this);}
00250 Atoms_iterator atoms_end() {return Atoms_iterator(*this,true);}
00251
00253 Atoms_const_iterator atoms_begin() const {return Atoms_const_iterator(*this);}
00255 Atoms_const_iterator atoms_end() const {return Atoms_const_iterator(*this,true);}
00256
00257
00258
00259
00260 DECLARE_AND_ACCESS(model_number,int)
00261
00262 };
00263
00264
00268 template<class System>
00269 class Molecular_chain{
00270 public:
00271 typedef typename System::Residue Residue;
00272 typedef typename Residue::Atom Atom;
00273 typedef std::map<std::pair<int,char>,Residue> Residue_container;
00274 typedef typename System::Model Model;
00275 private:
00276 typedef Molecular_chain<System> Self;
00277 const Model& model_;
00278 Residue_container residue_container_;
00279 public:
00280
00281 template<class Line_format>
00282 Molecular_chain(const Line_format& line_format,const std::string& line, const Model& mod):
00283 model_(mod),
00284 chain_identifier_(line_format.get_chain_identifier(line)) {}
00285
00286 Molecular_chain(char id, const Model& mod):model_(mod),chain_identifier_(id) {}
00287
00288 const Model& model() const {return model_;}
00289
00290 template<class Line_format>
00291 Residue& get_or_create_residue(const Line_format& line_format,const std::string& line){
00292 int ressn=line_format.get_residue_sequence_number(line);
00293 char insc=line_format.get_insertion_code(line);
00294 typename Residue_container::iterator it=residue_container_.find(std::make_pair(ressn,insc));
00295 if (it==residue_container_.end())
00296 it=residue_container_.insert( std::make_pair(std::make_pair(ressn,insc),Residue(line_format,line,*this) ) ).first;
00297 return it->second;
00298 }
00299
00300 Residue& get_or_create_residue(const std::string& resname,int ressn,char insc){
00301 typename Residue_container::iterator it=residue_container_.find(std::make_pair(ressn,insc));
00302 if (it==residue_container_.end())
00303 it=residue_container_.insert( std::make_pair(std::make_pair(ressn,insc),Residue(resname,ressn,insc,*this) ) ).first;
00304 return it->second;
00305 }
00306
00307 const Residue& get_residue(int ressn,char insc=' ') const {
00308 typename Residue_container::const_iterator it=residue_container_.find(std::make_pair(ressn,insc));
00309 assert (it!=residue_container_.end());
00310 return it->second;
00311 }
00312
00313 const typename System::Atom get_atom(int ressn,char insc,unsigned atom_sn) const {
00314 return get_residue(ressn,insc).get_atom(atom_sn);
00315 }
00316
00317 size_t number_of_residues() const {
00318 return residue_container_.size();
00319 }
00320
00321 size_t number_of_atoms() const {
00322 size_t total=0;
00323 for (typename Residue_container::const_iterator it=residue_container_.begin();it!=residue_container_.end();++it)
00324 total+=it->second.number_of_atoms();
00325 return total;
00326 }
00327
00328
00329
00330
00331 static const Residue& dereference (typename Residue_container::const_iterator it) {return it->second;}
00332 static Residue& dereference (typename Residue_container::iterator it) {return it->second;}
00333
00335 typedef internal::Residues_iterator_from_chain<Self,true> Residues_const_iterator;
00337 typedef internal::Residues_iterator_from_chain<Self,false> Residues_iterator;
00338
00340 Residues_iterator residues_begin() {return Residues_iterator(residue_container_.begin());}
00342 Residues_iterator residues_end() {return Residues_iterator(residue_container_.end());}
00343
00345 Residues_const_iterator residues_begin() const {return Residues_const_iterator(residue_container_.begin());}
00347 Residues_const_iterator residues_end() const {return Residues_const_iterator(residue_container_.end());}
00348
00350 typedef internal::Atoms_iterator_from_chain<Self,true> Atoms_const_iterator;
00352 typedef internal::Atoms_iterator_from_chain<Self,false> Atoms_iterator;
00353
00355 Atoms_iterator atoms_begin() {return Atoms_iterator(*this);}
00357 Atoms_iterator atoms_end() {return Atoms_iterator(*this,true);}
00358
00360 Atoms_const_iterator atoms_begin() const {return Atoms_const_iterator(*this);}
00362 Atoms_const_iterator atoms_end() const {return Atoms_const_iterator(*this,true);}
00363
00364
00365 DECLARE_AND_ACCESS(chain_identifier,char)
00366 };
00367
00371 template<class System>
00372 class Molecular_residue{
00373 public:
00374 typedef typename System::Atom Atom;
00375 typedef std::map<unsigned,Atom> Atom_container;
00376 typedef typename System::Chain Chain;
00377 private:
00378 typedef Molecular_residue<System> Self;
00379 const Chain& chain_;
00380 protected:
00381 Atom_container atom_container_;
00382 public:
00383 const Chain& chain() const {return chain_;}
00384 char chain_identifier() const {return chain_.chain_identifier();}
00385
00386 template<class Line_format>
00387 Molecular_residue(const Line_format& line_format, const std::string& line,const Chain& ch):
00388 chain_(ch),
00389 residue_name_(line_format.get_residue_name(line)),
00390 residue_sequence_number_(line_format.get_residue_sequence_number(line)),
00391 insertion_code_(line_format.get_insertion_code(line)){}
00392
00393 Molecular_residue(const std::string& resname,int index,char insc,const Chain& ch):
00394 chain_(ch),residue_name_(resname),residue_sequence_number_(index),insertion_code_(insc){}
00395
00396 template<class Line_format>
00397 void add_atom(const Line_format& line_format, const std::string& line)
00398 {
00399 unsigned sn=line_format.get_atom_serial_number(line);
00400 assert (atom_container_.find(sn)==atom_container_.end() || !"Two atoms with same serial numbers.");
00401 atom_container_.insert(std::make_pair(sn,Atom(line_format,line,*this)));
00402 }
00403
00404 size_t number_of_atoms() const {
00405 return atom_container_.size();
00406 }
00407
00408 const Atom& get_atom(unsigned sn) const {
00409 typename Atom_container::const_iterator it=atom_container_.find(sn);
00410 assert(atom_container_.find(sn)!=atom_container_.end());
00411 return it->second;
00412 }
00413
00414
00415
00416
00417 static const Atom& dereference (typename Atom_container::const_iterator it) {return it->second;}
00418 static Atom& dereference (typename Atom_container::iterator it) {return it->second;}
00419
00421 typedef internal::Atoms_iterator_from_residue<Self,true> Atoms_const_iterator;
00423 typedef internal::Atoms_iterator_from_residue<Self,false> Atoms_iterator;
00424
00426 Atoms_iterator atoms_begin() {return Atoms_iterator(atom_container_.begin(),atom_container_.end());}
00428 Atoms_iterator atoms_end() {return Atoms_iterator(atom_container_.end());}
00429
00431 Atoms_const_iterator atoms_begin() const {return Atoms_const_iterator(atom_container_.begin(),atom_container_.end());}
00433 Atoms_const_iterator atoms_end() const {return Atoms_const_iterator(atom_container_.end());}
00434
00435
00436 DECLARE_AND_ACCESS(residue_name,std::string)
00437 DECLARE_AND_ACCESS(residue_sequence_number,int)
00438 DECLARE_AND_ACCESS(insertion_code,char)
00439 };
00440
00441
00446 template<class System_,class Point>
00447 class Molecular_atom: public Point{
00448 public:
00449 typedef System_ System;
00450 typedef Point Point_3;
00451 typedef typename System::Residue Residue;
00452
00453 private:
00454 const Residue* residue_;
00455 public:
00456
00457 template <class Line_format,class Residue_type>
00458 Molecular_atom(const Line_format& line_format, const std::string& line,const Residue_type& res):
00459 Point(line_format.get_x(line),line_format.get_y(line),line_format.get_z(line)),
00460 residue_(static_cast<const Residue*>(&res)),
00461 is_hetatm_(line_format.is_hetatm()),
00462 atom_serial_number_(line_format.get_atom_serial_number(line)),
00463 atom_name_(line_format.get_atom_name(line)),
00464 alternate_location_(line_format.get_alternate_location(line)),
00465 occupancy_(line_format.get_occupancy(line)),
00466 temperature_factor_(line_format.get_temperature_factor(line)),
00467 element_(line_format.get_element(line)),
00468 charge_(line_format.get_charge(line))
00469 {
00470
00471
00472
00473
00474 }
00475
00476 Molecular_atom():Point(),residue_(NULL){}
00477
00478 Molecular_atom(double x,double y,double z):Point(x,y,z),residue_(NULL){}
00479
00480
00481 int system_index() const {return residue_->chain().model().system().index();};
00482
00483
00484 char chain_identifier() const {return residue_->chain().chain_identifier();}
00485
00486 const Residue& residue() const {return *residue_;}
00487 const std::string& residue_name() const {return residue_->residue_name();}
00488 int residue_sequence_number() const {return residue_->residue_sequence_number();}
00489 char insertion_code() const {return residue_->insertion_code();}
00490
00491
00492 DECLARE_AND_ACCESS(is_hetatm,bool)
00493 DECLARE_AND_ACCESS(atom_serial_number,int)
00494 DECLARE_AND_ACCESS(atom_name,std::string)
00495 DECLARE_AND_ACCESS(alternate_location,char)
00496 DECLARE_AND_ACCESS(occupancy,double)
00497 DECLARE_AND_ACCESS(temperature_factor,double)
00498 DECLARE_AND_ACCESS(element,std::string)
00499 DECLARE_AND_ACCESS(charge,int)
00500 };
00501
00502
00508 struct Default_system_items{
00509 template <class System,class Point>
00510 struct Model_wrapper{
00511 typedef Molecular_model<System> Type;
00512 };
00513
00514 template <class System,class Point>
00515 struct Chain_wrapper{
00516 typedef Molecular_chain<System> Type;
00517 };
00518
00519 template <class System,class Point>
00520 struct Residue_wrapper{
00521 typedef Molecular_residue<System> Type;
00522 };
00523
00524 template <class System,class Point>
00525 struct Atom_wrapper{
00526 typedef Molecular_atom<System,Point> Type;
00527 };
00528 };
00529
00530
00531
00532
00533 template <class System>
00534 char get_chain_identifier(const Molecular_chain<System>& c) {return c.chain_identifier();}
00535
00536 template <class System>
00537 const std::string& get_residue_name(const Molecular_residue<System>& r) {return r.residue_name();}
00538 template <class System>
00539 int get_residue_sequence_number(const Molecular_residue<System>& r) {return r.residue_sequence_number();}
00540 template <class System>
00541 char get_insertion_code(const Molecular_residue<System>& r) {return r.insertion_code();}
00542
00543 template <class System,class Point>
00544 bool get_is_hetatm(const Molecular_atom<System,Point>& a) {return a.is_hetatm() ;}
00545 template <class System,class Point>
00546 int get_atom_serial_number(const Molecular_atom<System,Point>& a) {return a.atom_serial_number() ;}
00547 template <class System,class Point>
00548 const std::string& get_atom_name(const Molecular_atom<System,Point>& a) {return a.atom_name() ;}
00549 template <class System,class Point>
00550 char get_alternate_location(const Molecular_atom<System,Point>& a) {return a.alternate_location() ;}
00551 template <class System,class Point>
00552 double get_occupancy(const Molecular_atom<System,Point>& a) {return a.occupancy() ;}
00553 template <class System,class Point>
00554 double get_temperature_factor(const Molecular_atom<System,Point>& a) {return a.temperature_factor() ;}
00555 template <class System,class Point>
00556 const std::string& get_element(const Molecular_atom<System,Point>& a) {return a.element() ;}
00557 template <class System,class Point>
00558 int get_charge(const Molecular_atom<System,Point>& a) {return a.charge() ;}
00559 template <class System,class Point>
00560 char get_chain_identifier(const Molecular_atom<System,Point>& a) {return a.chain_identifier() ;}
00561 template <class System,class Point>
00562 const std::string& get_residue_name(const Molecular_atom<System,Point>& a) {return a.residue_name() ;}
00563 template <class System,class Point>
00564 int get_residue_sequence_number(const Molecular_atom<System,Point>& a) {return a.residue_sequence_number() ;}
00565 template <class System,class Point>
00566 char get_insertion_code(const Molecular_atom<System,Point>& a) {return a.insertion_code() ;}
00567 template <class System,class Point>
00568 char get_x(const Molecular_atom<System,Point>& a) {return a.x() ;}
00569 template <class System,class Point>
00570 char get_y(const Molecular_atom<System,Point>& a) {return a.y() ;}
00571 template <class System,class Point>
00572 char get_z(const Molecular_atom<System,Point>& a) {return a.z() ;}
00573
00574
00575
00576
00577
00578
00579
00580
00581
00582
00583
00584
00585
00586
00587
00588 }
00589
00590 #endif //ESBTL_MOLECULAR_SYSTEM_H