ViewVC Help
View File | Revision Log | Show Annotations | View Changeset | Root Listing
root/group/trunk/OOPSE-3.0/src/types/MoleculeStamp.cpp
(Generate patch)

Comparing trunk/OOPSE-3.0/src/types/MoleculeStamp.cpp (file contents):
Revision 2204 by gezelter, Fri Apr 15 22:04:00 2005 UTC vs.
Revision 2483 by tim, Mon Dec 5 18:23:30 2005 UTC

# Line 39 | Line 39
39   * such damages.
40   */
41  
42 #include <stdlib.h>
43 #include <stdio.h>
44 #include <string.h>
42   #include <iostream>
43 <
43 > #include <functional>
44   #include "types/MoleculeStamp.hpp"
45 + #include "utils/Tuple.hpp"
46  
47 < char MoleculeStamp::errMsg[500];
47 > namespace oopse {
48 > MoleculeStamp::MoleculeStamp() {
49 >    DefineParameter(Name, "name");
50 >    
51 >    deprecatedKeywords_.insert("nAtoms");
52 >    deprecatedKeywords_.insert("nBonds");
53 >    deprecatedKeywords_.insert("nBends");
54 >    deprecatedKeywords_.insert("nTorsions");
55 >    deprecatedKeywords_.insert("nRigidBodies");
56 >    deprecatedKeywords_.insert("nCutoffGroups");
57 >    
58 > }
59  
60 < MoleculeStamp::MoleculeStamp(){
52 <  
53 <  n_atoms = 0;
54 <  n_bonds = 0;
55 <  n_bends = 0;
56 <  n_torsions = 0;
57 <  n_rigidbodies = 0;
58 <  n_cutoffgroups = 0;
59 <  n_integrable = 0;
60 > MoleculeStamp::~MoleculeStamp() {
61  
62 <  unhandled = NULL;
62 <  atoms = NULL;
63 <  bonds = NULL;
64 <  bends = NULL;
65 <  torsions = NULL;
66 <  rigidBodies = NULL;
67 <  cutoffGroups = NULL;
62 > }
63  
64 <  have_name = 0;
65 <  have_atoms = 0;
66 <  have_bonds = 0;
67 <  have_bends = 0;
68 <  have_torsions = 0;
69 <  have_rigidbodies = 0;
70 <  have_cutoffgroups = 0;
64 > bool MoleculeStamp::addAtomStamp( AtomStamp* atom) {
65 >    bool ret = addIndexSensitiveStamp(atomStamps_, atom);
66 >    if (!ret) {
67 >        std::cout << "multiple atoms have the same index: " << atom->getIndex() <<" in " << getName()  << " Molecule\n";
68 >    }
69 >    return ret;
70 >    
71 > }
72  
73 + bool MoleculeStamp::addBondStamp( BondStamp* bond) {
74 +    bondStamps_.push_back(bond);
75 +    return true;
76   }
77  
78 < MoleculeStamp::~MoleculeStamp(){
79 <  int i;
80 <  
81 <  if( unhandled != NULL) delete unhandled;
83 <  
84 <  if( rigidBodies != NULL ) {
85 <    for( i=0; i<n_rigidbodies; i++ ) delete rigidBodies[i];
86 <  }
87 <  delete[] rigidBodies;
78 > bool MoleculeStamp::addBendStamp( BendStamp* bend) {
79 >    bendStamps_.push_back(bend);
80 >    return true;
81 > }
82  
83 <  if( cutoffGroups != NULL ) {
84 <    for( i=0; i<n_cutoffgroups; i++ ) delete cutoffGroups[i];
85 <  }
86 <  delete[] cutoffGroups;
93 <  
94 <  if( atoms != NULL ){
95 <    for( i=0; i<n_atoms; i++ ) delete atoms[i];
96 <  }
97 <  delete[] atoms;
98 <  
99 <  if( bonds != NULL ){
100 <    for( i=0; i<n_bonds; i++ ) delete bonds[i];
101 <  }
102 <  delete[] bonds;
103 <  
104 <  if( bends != NULL ){
105 <    for( i=0; i<n_bends; i++ ) delete bends[i];
106 <  }
107 <  delete[] bends;
108 <  
109 <  if( torsions != NULL ){
110 <    for( i=0; i<n_torsions; i++ ) delete torsions[i];
111 <  }
112 <  delete[] torsions;
113 <  
83 > bool MoleculeStamp::addTorsionStamp( TorsionStamp* torsion) {
84 >    torsionStamps_.push_back(torsion);
85 >    return true;
86 > }
87  
88 <
89 <
88 > bool MoleculeStamp::addRigidBodyStamp( RigidBodyStamp* rigidbody) {
89 >    bool ret = addIndexSensitiveStamp(rigidBodyStamps_, rigidbody);
90 >    if (!ret) {
91 >        std::cout << "multiple rigidbodies have the same index: " << rigidbody->getIndex() <<" in " << getName()  << " Molecule\n";
92 >    }
93 >    return ret;
94   }
95  
96 < char* MoleculeStamp::assignString( char* lhs, char* rhs ){
97 <  
98 <  if( !strcmp( lhs, "name" ) ){
122 <    strcpy( name, rhs );
123 <    have_name = 1;
124 <  }
125 <  else{
126 <    if( unhandled == NULL ) unhandled = new LinkedAssign( lhs, rhs );
127 <    else unhandled->add( lhs, rhs );
128 <    have_extras = 1;
129 <  }
130 <  return NULL;
96 > bool MoleculeStamp::addCutoffGroupStamp( CutoffGroupStamp* cutoffgroup) {
97 >    cutoffGroupStamps_.push_back(cutoffgroup);
98 >    return true;
99   }
100  
101 < char* MoleculeStamp::assignDouble( char* lhs, double rhs ){
102 <  int i;
103 <
136 <  if( !strcmp( lhs, "nAtoms" ) ){
137 <    n_atoms = (int)rhs;
101 > bool MoleculeStamp::addFragmentStamp( FragmentStamp* fragment) {
102 >    return addIndexSensitiveStamp(fragmentStamps_, fragment);
103 > }
104      
105 <    if( have_atoms ){
106 <      sprintf( errMsg,
141 <               "MoleculeStamp error, n_atoms already declared"
142 <               " for molecule: %s\n",
143 <               name);
144 <      return strdup( errMsg );
145 <    }
146 <    have_atoms = 1;
147 <    atoms = new AtomStamp*[n_atoms];
148 <    for( i=0; i<n_atoms; i++ ) atoms[i] = NULL;
149 <  }
150 <  
151 <  else if( !strcmp( lhs, "nBonds" ) ){
152 <    n_bonds = (int)rhs;
105 > void MoleculeStamp::validate() {
106 >    DataHolder::validate();
107  
108 <    if( have_bonds ){
109 <      sprintf( errMsg,  
110 <               "MoleculeStamp error, n_bonds already declared for"
111 <               " molecule: %s\n",
112 <               name);
159 <      return strdup( errMsg );
108 >    atom2Rigidbody.resize(getNAtoms());
109 >    // negative number means atom is a free atom, does not belong to rigidbody
110 >    //every element in atom2Rigidbody has unique negative number at the very beginning
111 >    for(int i = 0; i < atom2Rigidbody.size(); ++i) {
112 >        atom2Rigidbody[i] = -1 - i;
113      }
114 <    have_bonds = 1;
115 <    bonds = new BondStamp*[n_bonds];
116 <    for( i=0; i<n_bonds; i++ ) bonds[i] = NULL;
117 <  }
118 <  
119 <  else if( !strcmp( lhs, "nBends" ) ){
167 <    n_bends = (int)rhs;
168 <
169 <    if( have_bends ){
170 <      sprintf( errMsg,
171 <               "MoleculeStamp error, n_bends already declared for"
172 <               " molecule: %s\n",
173 <               name);
174 <      return strdup( errMsg );
114 >    for (int i = 0; i < getNRigidBodies(); ++i) {
115 >        RigidBodyStamp* rbStamp = getRigidBodyStamp(i);
116 >        std::vector<int> members = rbStamp->getMembers();
117 >        for(std::vector<int>::iterator j = members.begin(); j != members.end(); ++j) {
118 >            atom2Rigidbody[*j] = i;                
119 >        }
120      }
176    have_bends = 1;
177    bends = new BendStamp*[n_bends];
178    for( i=0; i<n_bends; i++ ) bends[i] = NULL;
179  }
180  
181  else if( !strcmp( lhs, "nTorsions" ) ){
182    n_torsions = (int)rhs;
121  
122 <    if( have_torsions ){
123 <      sprintf( errMsg,
124 <               "MoleculeStamp error, n_torsions already declared for"
125 <               " molecule: %s\n",
126 <               name );
127 <      return strdup( errMsg );
122 >    checkAtoms();
123 >    checkBonds();
124 >    fillBondInfo();
125 >    checkBends();
126 >    checkTorsions();
127 >    checkRigidBodies();
128 >    checkCutoffGroups();
129 >    checkFragments();
130 >
131 >    int nrigidAtoms = 0;
132 >    for (int i = 0; i < getNRigidBodies(); ++i) {
133 >        RigidBodyStamp* rbStamp = getRigidBodyStamp(i);
134 >        nrigidAtoms += rbStamp->getNMembers();
135      }
136 <    have_torsions = 1;
192 <    torsions = new TorsionStamp*[n_torsions];
193 <    for( i=0; i<n_torsions; i++ ) torsions[i] = NULL;
194 <  }
136 >    nintegrable_ = getNAtoms()+ getNRigidBodies() - nrigidAtoms;
137  
138 <  else if( !strcmp( lhs, "nRigidBodies" ) ){
197 <    n_rigidbodies = (int)rhs;
138 > }
139  
140 <    if( have_rigidbodies ){
141 <      sprintf( errMsg,
142 <               "MoleculeStamp error, n_rigidbodies already declared for"
143 <               " molecule: %s\n",
203 <               name );
204 <      return strdup( errMsg );
140 > void MoleculeStamp::checkAtoms() {
141 >    std::vector<AtomStamp*>::iterator ai = std::find(atomStamps_.begin(), atomStamps_.end(), static_cast<AtomStamp*>(NULL));
142 >    if (ai != atomStamps_.end()) {
143 >        std::cout << "Error in Molecule " << getName() << ": atom[" << ai - atomStamps_.begin()<< "] is missing\n";
144      }
206    have_rigidbodies = 1;
207    rigidBodies = new RigidBodyStamp*[n_rigidbodies];
208    for( i=0; i<n_rigidbodies; i++ ) rigidBodies[i] = NULL;
209  }
145  
146 <  else if( !strcmp( lhs, "nCutoffGroups" ) ){
147 <    n_cutoffgroups = (int)rhs;
148 <
149 <    if( have_cutoffgroups ){
150 <      sprintf( errMsg,
151 <               "MoleculeStamp error, n_cutoffgroups already declared for"
152 <               " molecule: %s\n",
218 <               name );
219 <      return strdup( errMsg );
146 >    //make sure index is not out of range
147 >    int natoms = getNAtoms();
148 >    for(int i = 0; i < getNBonds(); ++i) {
149 >        BondStamp* bondStamp = getBondStamp(i);
150 >        if (bondStamp->getA() >=  natoms && bondStamp->getB() >= natoms) {
151 >            std::cout << "Error in Molecule " << getName() <<  ": bond between " << bondStamp->getA() << " and " << bondStamp->getB() << " is invalid\n";
152 >        }
153      }
221    have_cutoffgroups = 1;
222    cutoffGroups = new CutoffGroupStamp*[n_cutoffgroups];
223    for( i=0; i<n_cutoffgroups; i++ ) cutoffGroups[i] = NULL;
224  }
225  
226  else{
227    if( unhandled == NULL ) unhandled = new LinkedAssign( lhs, rhs );
228    else unhandled->add( lhs, rhs );
229    have_extras = 1;
230  }
231  return NULL;
154   }
155  
156 < char*  MoleculeStamp::assignInt( char* lhs, int rhs ){
157 <  int i;
158 <  
159 <  if( !strcmp( lhs, "nAtoms" ) ){
160 <    n_atoms = rhs;
156 > void MoleculeStamp::checkBonds() {
157 >    //make sure bonds are unique
158 >    std::set<std::pair<int, int> > allBonds;
159 >    for(int i = 0; i < getNBonds(); ++i) {
160 >        BondStamp* bondStamp= getBondStamp(i);        
161 >        std::pair<int, int> bondPair(bondStamp->getA(), bondStamp->getB());
162 >        //make sure bondTuple.first is always less than or equal to bondTuple.third
163 >        if (bondPair.first > bondPair.second) {
164 >            std::swap(bondPair.first, bondPair.second);
165 >        }
166 >        
167 >        std::set<std::pair<int, int> >::iterator iter = allBonds.find(bondPair);
168 >        if ( iter != allBonds.end()) {
169 >            std::cout << "Error in Molecule " << getName() << ": " << "Bond appears multiple times\n";
170 >        } else {
171 >            allBonds.insert(bondPair);
172 >        }
173 >    }
174      
175 <    if( have_atoms ){
176 <      sprintf( errMsg,
177 <               "MoleculeStamp error, n_atoms already declared for"
178 <               " molecule: %s\n",
179 <               name);
180 <      return strdup( errMsg );
175 >    //make sure atoms belong to same rigidbody do not bond to each other
176 >    for(int i = 0; i < getNBonds(); ++i) {
177 >        BondStamp* bondStamp = getBondStamp(i);
178 >        if (atom2Rigidbody[bondStamp->getA()] == atom2Rigidbody[bondStamp->getB()]) {
179 >            std::cout << "Error in Molecule " << getName() << ": "<<"bond between " << bondStamp->getA() << " and " << bondStamp->getB() << " belong to same rigidbody " << atom2Rigidbody[bondStamp->getA()] << "\n";
180 >        }
181      }
182 <    have_atoms = 1;
183 <    atoms = new AtomStamp*[n_atoms];
249 <    for( i=0; i<n_atoms; i++ ) atoms[i] = NULL;
250 <  }
251 <  
252 <  else if( !strcmp( lhs, "nBonds" ) ){
253 <    n_bonds = rhs;
182 >    
183 > }
184  
185 <    if( have_bonds ){
186 <      sprintf( errMsg,
187 <               "MoleculeStamp error, n_bonds already declared for"
188 <               " molecule: %s\n",
189 <               name);
260 <      return strdup( errMsg );
185 > struct BendLessThan : public std::binary_function<IntTuple4, IntTuple4, bool> {
186 >    bool operator()(IntTuple3 b1, IntTuple3 b2) {
187 >        return b1.first < b2.first
188 >             || (!(b2.first < b1.first) && b1.second < b2.second)
189 >             || (!(b2.first < b1.first) && !(b2.second < b2.second) && b1.third < b2.third);
190      }
191 <    have_bonds = 1;
263 <    bonds = new BondStamp*[n_bonds];
264 <    for( i=0; i<n_bonds; i++ ) bonds[i] = NULL;
265 <  }
266 <  
267 <  else if( !strcmp( lhs, "nBends" ) ){
268 <    n_bends = rhs;
191 > };
192  
193 <    if( have_bends ){
194 <      sprintf( errMsg,
195 <               "MoleculeStamp error, n_bends already declared for"
196 <               " molecule: %s\n",
197 <               name );
198 <      return strdup( errMsg );
199 <    }
200 <    have_bends = 1;
278 <    bends = new BendStamp*[n_bends];
279 <    for( i=0; i<n_bends; i++ ) bends[i] = NULL;
280 <  }
281 <  
282 <  else if( !strcmp( lhs, "nTorsions" ) ){
283 <    n_torsions = rhs;
193 > void MoleculeStamp::checkBends() {
194 >    for(int i = 0; i < getNBends(); ++i) {
195 >        BendStamp* bendStamp = getBendStamp(i);
196 >        std::vector<int> bendAtoms =  bendStamp->getMembers();
197 >        std::vector<int>::iterator j =std::find_if(bendAtoms.begin(), bendAtoms.end(), std::bind2nd(std::greater<int>(), getNAtoms()-1));
198 >        if (j != bendAtoms.end()) {
199 >            std::cout << "Error in Molecule " << getName();
200 >        }
201  
202 <    if( have_torsions ){
203 <      sprintf( errMsg,
204 <               "MoleculeStamp error, n_torsions already declared for"
205 <               " molecule: %s\n",
206 <               name);
207 <      return strdup( errMsg );
202 >        if (bendAtoms.size() == 2 ) {
203 >            if (!bendStamp->haveGhostVectorSource()) {
204 >                std::cout << "Error in Molecule " << getName() << ": ghostVectorSouce is missing\n";
205 >            }else{
206 >                int ghostIndex = bendStamp->getGhostVectorSource();
207 >                if (ghostIndex < getNAtoms()) {
208 >                    if (std::find(bendAtoms.begin(), bendAtoms.end(), ghostIndex) == bendAtoms.end()) {
209 >                      std::cout <<  "Error in Molecule " << getName() << ": ghostVectorSouce "<< ghostIndex<<"is invalid\n";
210 >                    }
211 >                    if (!getAtomStamp(ghostIndex)->haveOrientation()) {
212 >                        std::cout <<  "Error in Molecule " << getName() << ": ghost atom must be a directioanl atom\n";
213 >                    }
214 >                }else {
215 >                    std::cout << "Error in Molecule " << getName() <<  ": ghostVectorsource " << ghostIndex<< "  is invalid\n";
216 >                }
217 >            }
218 >        } else if (bendAtoms.size() == 3 && bendStamp->haveGhostVectorSource()) {
219 >            std::cout <<  "Error in Molecule " << getName() << ": normal bend should not have ghostVectorSouce\n";
220 >        }
221      }
292    have_torsions = 1;
293    torsions = new TorsionStamp*[n_torsions];
294    for( i=0; i<n_torsions; i++ ) torsions[i] = NULL;
295  }
222  
223 <  else if( !strcmp( lhs, "nRigidBodies" ) ){
224 <    n_rigidbodies = rhs;
225 <
226 <    if( have_rigidbodies ){
227 <      sprintf( errMsg,
228 <               "MoleculeStamp error, n_rigidbodies already declared for"
229 <               " molecule: %s\n",
230 <               name);
231 <      return strdup( errMsg );
232 <    }
233 <    have_rigidbodies = 1;
234 <    rigidBodies = new RigidBodyStamp*[n_rigidbodies];
235 <    for( i=0; i<n_rigidbodies; i++ ) rigidBodies[i] = NULL;
236 <  }
237 <  else if( !strcmp( lhs, "nCutoffGroups" ) ){
238 <    n_cutoffgroups = rhs;
239 <
240 <    if( have_cutoffgroups ){
241 <      sprintf( errMsg,
242 <               "MoleculeStamp error, n_cutoffgroups already declared for"
243 <               " molecule: %s\n",
244 <               name);
245 <      return strdup( errMsg );
246 <    }
247 <    have_cutoffgroups = 1;
248 <    cutoffGroups = new CutoffGroupStamp*[n_cutoffgroups];
249 <    for( i=0; i<n_cutoffgroups; i++ ) cutoffGroups[i] = NULL;
250 <  }
251 <  else{
252 <    if( unhandled == NULL ) unhandled = new LinkedAssign( lhs, rhs );
253 <    else unhandled->add( lhs, rhs );
254 <    have_extras = 1;
255 <  }
256 <  return NULL;
257 < }
258 <
259 < char* MoleculeStamp::addAtom( AtomStamp* the_atom, int atomIndex ){
260 <  
261 <  if( have_atoms && atomIndex < n_atoms ) atoms[atomIndex] = the_atom;
262 <  else {
263 <    if( have_atoms ){
264 <      sprintf( errMsg, "MoleculeStamp error, %d out of nAtoms range",
265 <               atomIndex );
266 <      return strdup( errMsg );
267 <    }
268 <    else return strdup("MoleculeStamp error, nAtoms not given before"
269 <                       " first atom declaration." );
270 <  }
223 >    for(int i = 0; i < getNBends(); ++i) {
224 >        BendStamp* bendStamp = getBendStamp(i);
225 >        std::vector<int> bendAtoms =  bendStamp->getMembers();
226 >        std::vector<int> rigidSet(getNRigidBodies(), 0);
227 >        std::vector<int>::iterator j;
228 >        for( j = bendAtoms.begin(); j != bendAtoms.end(); ++j) {
229 >            int rigidbodyIndex = atom2Rigidbody[*j];
230 >            if (rigidbodyIndex >= 0) {
231 >                ++rigidSet[rigidbodyIndex];
232 >                if (rigidSet[rigidbodyIndex] > 1) {
233 >                    std::cout << "Error in Molecule " << getName() << ": ";
234 >                    //std::cout << "atoms of bend " <<  << "belong to same rigidbody " << rigidbodyIndex << "\n";                    
235 >                }
236 >            }
237 >        }
238 >    }
239 >    
240 >    
241 >    std::set<IntTuple3, BendLessThan> allBends;
242 >    std::set<IntTuple3, BendLessThan>::iterator iter;
243 >    for(int i = 0; i < getNBends(); ++i) {
244 >        BendStamp* bendStamp= getBendStamp(i);
245 >        std::vector<int> bend = bendStamp->getMembers();
246 >        if (bend.size() == 2) {
247 >        // in case we have two ghost bend. For example,
248 >        // bend {
249 >        // members (0, 1);
250 >        //   ghostVectorSource = 0;
251 >        // }
252 >        // and
253 >        // bend {
254 >        //   members (0, 1);
255 >        // ghostVectorSource = 0;
256 >        // }
257 >        // In order to distinguish them. we expand them to Tuple3.
258 >        // the first one is expanded to (0, 0, 1) while the second one is expaned to (0, 1, 1)
259 >             int ghostIndex = bendStamp->getGhostVectorSource();
260 >             std::vector<int>::iterator j = std::find(bend.begin(), bend.end(), ghostIndex);
261 >             if (j != bend.end()) {
262 >                bend.insert(j, ghostIndex);
263 >             }
264 >        }
265 >        
266 >        IntTuple3 bendTuple(bend[0], bend[1], bend[2]);
267 >        //make sure bendTuple.first is always less than or equal to bendTuple.third
268 >        if (bendTuple.first > bendTuple.third) {
269 >            std::swap(bendTuple.first, bendTuple.third);
270 >        }
271 >        
272 >        iter = allBends.find(bendTuple);
273 >        if ( iter != allBends.end()) {
274 >            std::cout << "Error in Molecule " << getName() << ": " << "Bend appears multiple times\n";
275 >        } else {
276 >            allBends.insert(bendTuple);
277 >        }
278 >    }
279  
280 <  return NULL;
281 < }
280 >    for (int i = 0; i < getNBonds(); ++i) {
281 >        BondStamp* bondStamp = getBondStamp(i);
282 >        int a = bondStamp->getA();
283 >        int b = bondStamp->getB();
284  
285 < char* MoleculeStamp::addRigidBody( RigidBodyStamp* the_rigidbody,
286 <                                   int rigidBodyIndex ){
351 <  
352 <  if( have_rigidbodies && rigidBodyIndex < n_rigidbodies )
353 <    rigidBodies[rigidBodyIndex] = the_rigidbody;
354 <  else {
355 <    if( have_rigidbodies ){
356 <      sprintf( errMsg, "MoleculeStamp error, %d out of nRigidBodies range",
357 <               rigidBodyIndex );
358 <      return strdup( errMsg );
359 <    }
360 <    else return strdup("MoleculeStamp error, nRigidBodies not given before"
361 <                       " first rigidBody declaration." );
362 <  }
363 <  
364 <  return NULL;
365 < }
285 >        AtomStamp* atomA = getAtomStamp(a);
286 >        AtomStamp* atomB = getAtomStamp(b);
287  
288 < char* MoleculeStamp::addCutoffGroup( CutoffGroupStamp* the_cutoffgroup,
289 <                                     int cutoffGroupIndex ){
290 <  
291 <  if( have_cutoffgroups && cutoffGroupIndex < n_cutoffgroups )
292 <    cutoffGroups[cutoffGroupIndex] = the_cutoffgroup;
293 <  else {
294 <    if( have_cutoffgroups ){
295 <      sprintf( errMsg, "MoleculeStamp error, %d out of nCutoffGroups range",
296 <               cutoffGroupIndex );
297 <      return strdup( errMsg );
298 <    }
378 <    else return strdup("MoleculeStamp error, nCutoffGroups not given before"
379 <                       " first CutoffGroup declaration." );
380 <  }
381 <  
382 <  return NULL;
383 < }
288 >        //find bend c--a--b
289 >        AtomStamp::AtomIter ai;
290 >        for(int c= atomA->getFirstBonedAtom(ai);c != -1;c = atomA->getNextBonedAtom(ai))
291 >        {
292 >            if(b == c)
293 >                continue;          
294 >            
295 >            IntTuple3 newBend(c, a, b);
296 >            if (newBend.first > newBend.third) {
297 >                std::swap(newBend.first, newBend.third);
298 >            }
299  
300 < char* MoleculeStamp::addBond( BondStamp* the_bond, int bondIndex ){
301 <  
302 <  
303 <  if( have_bonds && bondIndex < n_bonds ) bonds[bondIndex] = the_bond;
304 <  else{
305 <    if( have_bonds ){
306 <      sprintf( errMsg, "MoleculeStamp error, %d out of nBonds range",
392 <               bondIndex );
393 <      return strdup( errMsg );
394 <    }
395 <    else return strdup("MoleculeStamp error, nBonds not given before"
396 <                       "first bond declaration." );
397 <  }
300 >            if (allBends.find(newBend) == allBends.end() ) {                
301 >                allBends.insert(newBend);
302 >                BendStamp * newBendStamp = new BendStamp();
303 >                newBendStamp->setMembers(newBend);
304 >                addBendStamp(newBendStamp);
305 >            }
306 >        }        
307  
308 <  return NULL;
309 < }
308 >        //find bend a--b--c
309 >        for(int c= atomB->getFirstBonedAtom(ai);c != -1;c = atomB->getNextBonedAtom(ai))
310 >        {
311 >            if(a == c)
312 >                continue;          
313  
314 < char* MoleculeStamp::addBend( BendStamp* the_bend, int bendIndex ){
315 <  
316 <  
317 <  if( have_bends && bendIndex < n_bends ) bends[bendIndex] = the_bend;
318 <  else{
319 <    if( have_bends ){
320 <      sprintf( errMsg, "MoleculeStamp error, %d out of nBends range",
321 <               bendIndex );
322 <      return strdup( errMsg );
314 >            IntTuple3 newBend( a, b, c);
315 >            if (newBend.first > newBend.third) {
316 >                std::swap(newBend.first, newBend.third);
317 >            }            
318 >            if (allBends.find(newBend) == allBends.end() ) {                
319 >                allBends.insert(newBend);
320 >                BendStamp * newBendStamp = new BendStamp();
321 >                newBendStamp->setMembers(newBend);
322 >                addBendStamp(newBendStamp);
323 >            }
324 >        }        
325      }
412    else return strdup("MoleculeStamp error, nBends not given before"
413                       "first bend declaration." );
414  }
326  
416  return NULL;
327   }
328  
329 < char* MoleculeStamp::addTorsion( TorsionStamp* the_torsion, int torsionIndex ){
330 <  
331 <  
332 <  if( have_torsions && torsionIndex < n_torsions )
333 <    torsions[torsionIndex] = the_torsion;
334 <  else{
335 <    if( have_torsions ){
426 <      sprintf( errMsg, "MoleculeStamp error, %d out of nTorsions range",
427 <               torsionIndex );
428 <      return strdup( errMsg );
329 > struct TorsionLessThan : public std::binary_function<IntTuple4, IntTuple4, bool> {
330 >    bool operator()(IntTuple4 t1, IntTuple4 t2) {
331 >
332 >        return t1.first < t2.first
333 >             || (!(t2.first < t1.first) && t1.second < t2.second)
334 >             || (!(t2.first < t1.first) && !(t2.second < t2.second) && t1.third < t2.third)
335 >             ||(!(t2.first < t1.first) && !(t2.second < t2.second) && !(t2.third < t1.third) && t1.fourth < t2.fourth);
336      }
430    else return strdup("MoleculeStamp error, nTorsions not given before"
431                       "first torsion declaration." );
432  }
337  
434  return NULL;
435 }
338  
437 char* MoleculeStamp::checkMe( void ){
438  
439  int i;
440  short int no_atom, no_rigidbody, no_cutoffgroup;
339  
340 <  if( !have_name ) return strdup( "MoleculeStamp error. Molecule's name"
443 <                                  " was not given.\n" );
444 <  
445 <  if( !have_atoms ){
446 <    return strdup( "MoleculeStamp error. Molecule contains no atoms." );
447 <  }
448 <  
449 <  no_rigidbody = 0;
450 <  for( i=0; i<n_rigidbodies; i++ ){
451 <    if( rigidBodies[i] == NULL ) no_rigidbody = 1;
452 <  }
340 > };
341  
454  if( no_rigidbody ){
455    sprintf( errMsg,
456             "MoleculeStamp error. Not all of the RigidBodies were"
457             " declared in molecule \"%s\".\n", name );
458    return strdup( errMsg );
459  }
342  
343 <  no_cutoffgroup = 0;
344 <  for( i=0; i<n_cutoffgroups; i++ ){
345 <    if( cutoffGroups[i] == NULL ) no_cutoffgroup = 1;
346 <  }
343 > void MoleculeStamp::checkTorsions() {
344 >    for(int i = 0; i < getNTorsions(); ++i) {
345 >        TorsionStamp* torsionStamp = getTorsionStamp(i);
346 >        std::vector<int> torsionAtoms =  torsionStamp->getMembers();
347 >        std::vector<int> rigidSet(getNRigidBodies(), 0);
348 >        std::vector<int>::iterator j;
349 >        for( j = torsionAtoms.begin(); j != torsionAtoms.end(); ++j) {
350 >            int rigidbodyIndex = atom2Rigidbody[*j];
351 >            if (rigidbodyIndex >= 0) {
352 >                ++rigidSet[rigidbodyIndex];
353 >                if (rigidSet[rigidbodyIndex] > 1) {
354 >                    std::cout << "Error in Molecule " << getName() << ": ";
355 >                    //std::cout << "atoms of torsion " <<  << "belong to same rigidbody " << rigidbodyIndex << "\n";                    
356 >                }
357 >            }
358 >        }
359 >    }    
360  
361 <  if( no_cutoffgroup ){
362 <    sprintf( errMsg,
363 <             "MoleculeStamp error. Not all of the CutoffGroups were"
364 <             " declared in molecule \"%s\".\n", name );
365 <    return strdup( errMsg );
366 <  }
367 <  
368 <  no_atom = 0;
369 <  for( i=0; i<n_atoms; i++ ){
370 <    if( atoms[i] == NULL ) no_atom = 1;
371 <  }
361 >    std::set<IntTuple4, TorsionLessThan> allTorsions;
362 >    std::set<IntTuple4, TorsionLessThan>::iterator iter;
363 >     for(int i = 0; i < getNTorsions(); ++i) {
364 >         TorsionStamp* torsionStamp= getTorsionStamp(i);
365 >         std::vector<int> torsion = torsionStamp->getMembers();
366 >         if (torsion.size() == 3) {
367 >             int ghostIndex = torsionStamp->getGhostVectorSource();
368 >             std::vector<int>::iterator j = std::find(torsion.begin(), torsion.end(), ghostIndex);
369 >             if (j != torsion.end()) {
370 >                torsion.insert(j, ghostIndex);
371 >             }
372 >         }
373  
374 <  if( no_atom ){
375 <    sprintf( errMsg,
376 <             "MoleculeStamp error. Not all of the atoms were"
377 <             " declared in molecule \"%s\".\n", name );
378 <    return strdup( errMsg );
483 <  }
374 >        IntTuple4 torsionTuple(torsion[0], torsion[1], torsion[2], torsion[3]);
375 >        if (torsionTuple.first > torsionTuple.fourth) {
376 >            std::swap(torsionTuple.first, torsionTuple.fourth);
377 >            std::swap(torsionTuple.second, torsionTuple.third);                    
378 >        }                
379  
380 <  n_integrable = n_atoms;
381 <  for (i = 0; i < n_rigidbodies; i++)
382 <    n_integrable = n_integrable - rigidBodies[i]->getNMembers() + 1; //rigidbody is an integrable object
383 <  
384 <  if (n_integrable <= 0 || n_integrable > n_atoms) {
385 <    sprintf( errMsg,
386 <             "MoleculeStamp error. n_integrable is either <= 0 or"
492 <             " greater than n_atoms in molecule \"%s\".\n", name );
493 <    return strdup( errMsg );
494 <  }
380 >         iter = allTorsions.find(torsionTuple);
381 >         if ( iter == allTorsions.end()) {
382 >            allTorsions.insert(torsionTuple);
383 >         } else {
384 >            std::cout << "Error in Molecule " << getName() << ": " << "Torsion appears multiple times\n";
385 >         }
386 >     }
387  
388 <  return NULL;
389 < }  
388 >    for (int i = 0; i < getNBonds(); ++i) {
389 >        BondStamp* bondStamp = getBondStamp(i);
390 >        int b = bondStamp->getA();
391 >        int c = bondStamp->getB();
392  
393 +        AtomStamp* atomB = getAtomStamp(b);
394 +        AtomStamp* atomC = getAtomStamp(c);
395  
396 +        AtomStamp::AtomIter ai2;
397 +        AtomStamp::AtomIter ai3;
398 +
399 +        for(int a = atomB->getFirstBonedAtom(ai2);a != -1;a = atomB->getNextBonedAtom(ai2))
400 +        {
401 +            if(a == c)
402 +                continue;
403 +
404 +            for(int d = atomC->getFirstBonedAtom(ai3);d != -1;d = atomC->getNextBonedAtom(ai3))
405 +            {
406 +                if(d == b)
407 +                    continue;
408 +                
409 +                IntTuple4 newTorsion(a, b, c, d);
410 +                //make sure the first element is always less than or equal to the fourth element in IntTuple4
411 +                if (newTorsion.first > newTorsion.fourth) {
412 +                    std::swap(newTorsion.first, newTorsion.fourth);
413 +                    std::swap(newTorsion.second, newTorsion.third);                    
414 +                }                
415 +                if (allTorsions.find(newTorsion) == allTorsions.end() ) {                
416 +                    allTorsions.insert(newTorsion);
417 +                    TorsionStamp * newTorsionStamp = new TorsionStamp();
418 +                    newTorsionStamp->setMembers(newTorsion);
419 +                    addTorsionStamp(newTorsionStamp);                    
420 +                }            
421 +            }
422 +        }    
423 +    }
424 +
425 + }
426 +
427 + void MoleculeStamp::checkRigidBodies() {
428 +     std::vector<RigidBodyStamp*>::iterator ri = std::find(rigidBodyStamps_.begin(), rigidBodyStamps_.end(), static_cast<RigidBodyStamp*>(NULL));
429 +     if (ri != rigidBodyStamps_.end()) {
430 +         std::cout << "Error in Molecule " << getName() << ":rigidBody[" <<  ri - rigidBodyStamps_.begin()<< "] is missing\n";
431 +     }
432 +
433 +    for (int i = 0; i < getNRigidBodies(); ++i) {
434 +        RigidBodyStamp* rbStamp = getRigidBodyStamp(i);
435 +        std::vector<int> rigidAtoms =  rbStamp ->getMembers();
436 +        std::vector<int>::iterator j =std::find_if(rigidAtoms.begin(), rigidAtoms.end(), std::bind2nd(std::greater<int>(), getNAtoms()-1));
437 +        if (j != rigidAtoms.end()) {
438 +            std::cout << "Error in Molecule " << getName();
439 +        }
440 +        
441 +    }    
442 + }
443 +
444 + void MoleculeStamp::checkCutoffGroups() {
445 +
446 +    for(int i = 0; i < getNCutoffGroups(); ++i) {
447 +        CutoffGroupStamp* cutoffGroupStamp = getCutoffGroupStamp(i);
448 +        std::vector<int> cutoffGroupAtoms =  cutoffGroupStamp ->getMembers();
449 +        std::vector<int>::iterator j =std::find_if(cutoffGroupAtoms.begin(), cutoffGroupAtoms.end(), std::bind2nd(std::greater<int>(), getNAtoms()-1));
450 +        if (j != cutoffGroupAtoms.end()) {
451 +            std::cout << "Error in Molecule " << getName() << ": cutoffGroup" << " is out of range\n";
452 +        }
453 +    }    
454 + }
455 +
456 + void MoleculeStamp::checkFragments() {
457 +
458 +    std::vector<FragmentStamp*>::iterator fi = std::find(fragmentStamps_.begin(), fragmentStamps_.end(), static_cast<FragmentStamp*>(NULL));
459 +    if (fi != fragmentStamps_.end()) {
460 +        std::cout << "Error in Molecule " << getName() << ":fragment[" <<  fi - fragmentStamps_.begin()<< "] is missing\n";
461 +    }
462 +    
463 + }
464 +
465 + void MoleculeStamp::fillBondInfo() {
466 +
467 +    for (int i = 0; i < getNBonds(); ++i) {
468 +        BondStamp* bondStamp = getBondStamp(i);
469 +        int a = bondStamp->getA();
470 +        int b = bondStamp->getB();
471 +        AtomStamp* atomA = getAtomStamp(a);
472 +        AtomStamp* atomB = getAtomStamp(b);
473 +        atomA->addBond(i);
474 +        atomA->addBondedAtom(b);
475 +        atomB->addBond(i);        
476 +        atomB->addBondedAtom(a);
477 +
478 +    }
479 + }
480 +
481 +
482 +
483   //Function Name: isBondInSameRigidBody
484   //Return true is both atoms of the bond belong to the same rigid body, otherwise return false
485   bool MoleculeStamp::isBondInSameRigidBody(BondStamp* bond){
# Line 544 | Line 527 | bool MoleculeStamp::isAtomInRigidBody(int atomIndex, i
527    numRb = this->getNRigidBodies();
528    
529    for(int i = 0 ; i < numRb; i++){
530 <    rbStamp = this->getRigidBody(i);
530 >    rbStamp = this->getRigidBodyStamp(i);
531      numAtom = rbStamp->getNMembers();
532      for(int j = 0; j < numAtom; j++)
533 <      if (rbStamp->getMember(j) == atomIndex){
533 >      if (rbStamp->getMemberAt(j) == atomIndex){
534          whichRigidBody = i;
535          consAtomIndex = j;
536          return true;
# Line 570 | Line 553 | std::vector<std::pair<int, int> > MoleculeStamp::getJo
553    int atomIndex2;
554    std::vector<std::pair<int, int> > jointAtomIndexPair;
555    
556 <  rbStamp1 = this->getRigidBody(rb1);
556 >  rbStamp1 = this->getRigidBodyStamp(rb1);
557    natomInRb1 =rbStamp1->getNMembers();
558  
559 <  rbStamp2 = this->getRigidBody(rb2);
559 >  rbStamp2 = this->getRigidBodyStamp(rb2);
560    natomInRb2 =rbStamp2->getNMembers();
561  
562    for(int i = 0; i < natomInRb1; i++){
563 <    atomIndex1 = rbStamp1->getMember(i);
563 >    atomIndex1 = rbStamp1->getMemberAt(i);
564        
565      for(int j= 0; j < natomInRb1; j++){
566 <      atomIndex2 = rbStamp2->getMember(j);
566 >      atomIndex2 = rbStamp2->getMemberAt(j);
567  
568        if(atomIndex1 == atomIndex2){
569          jointAtomIndexPair.push_back(std::make_pair(i, j));
570          break;
571        }
572        
573 <    }//end for(j =0)
573 >    }
574  
575 <  }//end for (i = 0)
575 >  }
576  
577    return jointAtomIndexPair;
578   }
579 +
580 + }

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines