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

Comparing trunk/OOPSE-4/src/applications/randomBuilder/randomBuilder.cpp (file contents):
Revision 2738 by chuckv, Tue Apr 25 22:59:27 2006 UTC vs.
Revision 3041 by gezelter, Tue Oct 10 18:34:12 2006 UTC

# Line 42 | Line 42
42   *
43   *  Created by Charles F. Vardeman II on 10 Apr 2006.
44   *  @author  Charles F. Vardeman II
45 < *  @version $Id: randomBuilder.cpp,v 1.1 2006-04-25 22:59:27 chuckv Exp $
45 > *  @version $Id: randomBuilder.cpp,v 1.6 2006-10-10 18:34:12 gezelter Exp $
46   *
47   */
48  
# Line 73 | Line 73 | void createMdFile(const std::string&oldMdFileName,
73  
74   void createMdFile(const std::string&oldMdFileName,
75                    const std::string&newMdFileName,
76 <                  int components,int* numMol);
76 >                  std::vector<int> nMol);
77  
78   int main(int argc, char *argv []) {
79  
80 <  //register force fields
80 >  // register force fields
81    registerForceFields();
82    registerLattice();
83      
84    gengetopt_args_info args_info;
85    std::string latticeType;
86    std::string inputFileName;
87 <  std::string outPrefix;
88 <  std::string outMdFileName;
89 <  std::string outInitFileName;
87 >  std::string outputFileName;
88    Lattice *simpleLat;
89 <  int* numMol;
90 <  double latticeConstant;
91 <  std::vector<double> lc;
92 <  double mass;
93 <  const double rhoConvertConst = 1.661;
96 <  double density;
97 <  int nx,
98 <    ny,
99 <    nz;
89 >  RealType latticeConstant;
90 >  std::vector<RealType> lc;
91 >  const RealType rhoConvertConst = 1.661;
92 >  RealType density;
93 >  int nx, ny, nz;
94    Mat3x3d hmat;
95    MoLocator *locator;
96    std::vector<Vector3d> latticePos;
97    std::vector<Vector3d> latticeOrt;
98 <  int numMolPerCell;
105 <  int curMolIndex;
98 >  int nMolPerCell;
99    DumpWriter *writer;
100  
101    // parse command line arguments
# Line 112 | Line 105 | int main(int argc, char *argv []) {
105    density = args_info.density_arg;
106  
107    //get lattice type
108 <  latticeType = UpperCase(args_info.latticetype_arg);
108 >  latticeType = "FCC";
109  
110    simpleLat = LatticeFactory::getInstance()->createLattice(latticeType);
111      
# Line 122 | Line 115 | int main(int argc, char *argv []) {
115      painCave.isFatal = 1;
116      simError();
117    }
118 +  nMolPerCell = simpleLat->getNumSitesPerCell();
119  
120 <  //get the number of unit cell
120 >  //get the number of unit cells in each direction:
121 >
122    nx = args_info.nx_arg;
123  
124    if (nx <= 0) {
125 <    std::cerr << "The number of unit cell in h direction must be greater than 0" << std::endl;
126 <    exit(1);
125 >    sprintf(painCave.errMsg, "The number of unit cells in the x direction "
126 >            "must be greater than 0.");
127 >    painCave.isFatal = 1;
128 >    simError();
129    }
130  
131    ny = args_info.ny_arg;
132  
133    if (ny <= 0) {
134 <    std::cerr << "The number of unit cell in l direction must be greater than 0" << std::endl;
135 <    exit(1);
134 >    sprintf(painCave.errMsg, "The number of unit cells in the y direction "
135 >            "must be greater than 0.");
136 >    painCave.isFatal = 1;
137 >    simError();
138    }
139  
140    nz = args_info.nz_arg;
141  
142    if (nz <= 0) {
143 <    std::cerr << "The number of unit cell in k direction must be greater than 0" << std::endl;
144 <    exit(1);
143 >    sprintf(painCave.errMsg, "The number of unit cells in the z direction "
144 >            "must be greater than 0.");
145 >    painCave.isFatal = 1;
146 >    simError();
147    }
148  
149 +  int nSites = nMolPerCell * nx * ny * nz;
150 +
151    //get input file name
152    if (args_info.inputs_num)
153      inputFileName = args_info.inputs[0];
154    else {
155 <    std::cerr << "You must specify a input file name.\n" << std::endl;
156 <    cmdline_parser_print_help();
157 <    exit(1);
155 >    sprintf(painCave.errMsg, "No input .md file name was specified "
156 >            "on the command line");
157 >    painCave.isFatal = 1;
158 >    simError();
159    }
160  
161    //parse md file and set up the system
162 +
163    SimCreator oldCreator;
164    SimInfo* oldInfo = oldCreator.createSim(inputFileName, false);
165    Globals* simParams = oldInfo->getSimParams();
166  
167 <  int nComponents =simParams->getNComponents();
163 <  if (oldInfo->getNMoleculeStamp()>= 2) {
164 <    std::cerr << "can not build the system with more than two components"
165 <              << std::endl;
166 <    exit(1);
167 <  }
167 >  // Calculate lattice constant (in Angstroms)
168  
169 <  //get mass of molecule.
169 >  std::vector<Component*> components = simParams->getComponents();
170 >  std::vector<RealType> molFractions;
171 >  std::vector<RealType> molecularMasses;
172 >  std::vector<int> nMol;
173 >  int nComponents = components.size();
174  
175 <  mass = getMolMass(oldInfo->getMoleculeStamp(0), oldInfo->getForceField());
175 >  if (nComponents == 1) {
176 >    molFractions.push_back(1.0);    
177 >  } else {
178 >    if (args_info.molFraction_given == nComponents) {
179 >      for (int i = 0; i < nComponents; i++) {
180 >        molFractions.push_back(args_info.molFraction_arg[i]);
181 >      }
182 >    } else if (args_info.molFraction_given == nComponents-1) {
183 >      RealType remainingFraction = 1.0;
184 >      for (int i = 0; i < nComponents-1; i++) {
185 >        molFractions.push_back(args_info.molFraction_arg[i]);
186 >        remainingFraction -= molFractions[i];
187 >      }
188 >      molFractions.push_back(remainingFraction);
189 >    } else {    
190 >      sprintf(painCave.errMsg, "randomBuilder can't figure out molFractions "
191 >              "for all of the components in the <MetaData> block.");
192 >      painCave.isFatal = 1;
193 >      simError();
194 >    }
195 >  }
196  
197 <  //creat lattice
198 <  simpleLat = LatticeFactory::getInstance()->createLattice(latticeType);
197 >  // do some sanity checking:
198 >  
199 >  RealType totalFraction = 0.0;
200  
201 <  if (simpleLat == NULL) {
202 <    std::cerr << "Error in creating lattice" << std::endl;
203 <    exit(1);
201 >  for (int i = 0; i < nComponents; i++) {
202 >    if (molFractions.at(i) < 0.0) {
203 >      sprintf(painCave.errMsg, "One of the requested molFractions was"
204 >              " less than zero!");
205 >      painCave.isFatal = 1;
206 >      simError();
207 >    }
208 >    if (molFractions.at(i) > 1.0) {
209 >      sprintf(painCave.errMsg, "One of the requested molFractions was"
210 >              " greater than one!");
211 >      painCave.isFatal = 1;
212 >      simError();
213 >    }
214 >    totalFraction += molFractions.at(i);
215    }
216 +  if (abs(totalFraction - 1.0) > 1e-6) {
217 +    sprintf(painCave.errMsg, "The sum of molFractions was not close enough to 1.0");
218 +    painCave.isFatal = 1;
219 +    simError();
220 +  }
221  
222 <  numMolPerCell = simpleLat->getNumSitesPerCell();
222 >  int remaining = nSites;
223 >  for (int i=0; i < nComponents-1; i++) {    
224 >    nMol.push_back(int((RealType)nSites * molFractions.at(i)));
225 >    remaining -= nMol.at(i);
226 >  }
227 >  nMol.push_back(remaining);
228  
229 <  //calculate lattice constant (in Angstrom)
184 <  latticeConstant = pow(rhoConvertConst * numMolPerCell * mass / density,
185 <                        1.0 / 3.0);
229 >  // recompute actual mol fractions and perform final sanity check:
230  
231 <  //set lattice constant
231 >  int totalMolecules = 0;
232 >  RealType totalMass = 0.0;
233 >  for (int i=0; i < nComponents; i++) {
234 >    molFractions[i] = (RealType)(nMol.at(i))/(RealType)nSites;
235 >    totalMolecules += nMol.at(i);
236 >    molecularMasses.push_back(getMolMass(oldInfo->getMoleculeStamp(i),
237 >                                         oldInfo->getForceField()));
238 >    totalMass += (RealType)(nMol.at(i)) * molecularMasses.at(i);
239 >  }
240 >  RealType avgMass = totalMass / (RealType) totalMolecules;
241 >
242 >  if (totalMolecules != nSites) {
243 >    sprintf(painCave.errMsg, "Computed total number of molecules is not equal "
244 >            "to the number of lattice sites!");
245 >    painCave.isFatal = 1;
246 >    simError();
247 >  }
248 >    
249 >  latticeConstant = pow(rhoConvertConst * nMolPerCell * avgMass / density,
250 >                        (RealType)(1.0 / 3.0));
251 >  
252 >  // Set the lattice constant
253 >  
254    lc.push_back(latticeConstant);
255    simpleLat->setLatticeConstant(lc);
256 +  
257 +  // Calculate the lattice sites and fill the lattice vector.
258  
259 <  //calculate the total number of molecules
192 <  int totMol = nx * ny * nz * numMolPerCell;
259 >  // Get the standard orientations of the cell sites
260  
261 <  // Calculate the lattice sites and fill lattice vector.
262 <  vector<Vector3d> latticeSites;
261 >  latticeOrt = simpleLat->getLatticePointsOrt();
262 >
263 >  vector<Vector3d> sites;
264 >  vector<Vector3d> orientations;
265    
266    for(int i = 0; i < nx; i++) {
267      for(int j = 0; j < ny; j++) {
268        for(int k = 0; k < nz; k++) {
269  
270 <        //get the position of the cell sites
270 >        // Get the position of the cell sites
271 >
272          simpleLat->getLatticePointsPos(latticePos, i, j, k);
273  
274 <        for(int l = 0; l < numMolPerCell; l++) {
275 <          latticeSites.push_back(latticePos[l]);
274 >        for(int l = 0; l < nMolPerCell; l++) {
275 >          sites.push_back(latticePos[l]);
276 >          orientations.push_back(latticeOrt[l]);
277          }
278        }
279      }
280    }
210
211  int numSites = latticeSites.size();
212
213  numMol = new int[nComponents];
214  if (nComponents != args_info.molFraction_given && nComponents != 1){
215    std::cerr << "Number of components does not equal molFraction occurances." << std::endl;
216    exit(1);
217  }
218  int totComponents = 0;
219  for (int i = 0;i<nComponents-1;i++){ /* Figure out Percent for each component */
220    numMol[i] = int((double)numSites * args_info.molFraction_arg[i]);
221    std::cout<<numMol[i]<<std::endl;
222    totComponents += numMol[i];
223  }
224  numMol[nComponents-1] = numSites - totComponents;
281    
282 +  outputFileName = args_info.output_arg;
283  
284 <  outPrefix = getPrefix(inputFileName.c_str()) + "_" + latticeType;
228 <  outMdFileName = outPrefix + ".md";
284 >  // create a new .md file on the fly which corrects the number of molecules
285  
286 <  //creat new .md file on fly which corrects the number of molecule    
231 <  createMdFile(inputFileName, outMdFileName, nComponents,numMol);
286 >  createMdFile(inputFileName, outputFileName, nMol);
287  
288 +  if (oldInfo != NULL)
289 +    delete oldInfo;
290  
291 +  // We need to read in the new SimInfo object, then Parse the
292 +  // md file and set up the system
293  
294 <  //determine the output file names  
295 <  if (args_info.output_given){
237 <    outInitFileName = args_info.output_arg;
238 <  }else{
239 <    outInitFileName = getPrefix(inputFileName.c_str()) + ".in";
240 <  }
294 >  SimCreator newCreator;
295 >  SimInfo* newInfo = newCreator.createSim(outputFileName, false);
296  
297 <  //fill Hmat
298 <  hmat(0, 0)= nx * latticeConstant;
297 >  // fill Hmat
298 >
299 >  hmat(0, 0) = nx * latticeConstant;
300    hmat(0, 1) = 0.0;
301    hmat(0, 2) = 0.0;
302  
# Line 252 | Line 308 | int main(int argc, char *argv []) {
308    hmat(2, 1) = 0.0;
309    hmat(2, 2) = nz * latticeConstant;
310  
311 <  //set Hmat
256 <  oldInfo->getSnapshotManager()->getCurrentSnapshot()->setHmat(hmat);
311 >  // Set Hmat
312  
313 <  //place the molecules
313 >  newInfo->getSnapshotManager()->getCurrentSnapshot()->setHmat(hmat);
314  
315 <  curMolIndex = 0;
315 >  // place the molecules
316  
317 <  //get the orientation of the cell sites
263 <  //for the same type of molecule in same lattice, it will not change
264 <  latticeOrt = simpleLat->getLatticePointsOrt();
317 >  // Randomize a vector of ints:
318  
319 <
320 <  /* Randomize position vector */
321 <  std::random_shuffle(latticeSites.begin(), latticeSites.end());
319 >  vector<int> ids;
320 >  for (int i = 0; i < sites.size(); i++) ids.push_back(i);
321 >  std::random_shuffle(ids.begin(), ids.end());
322  
270
271  if (oldInfo != NULL)
272    delete oldInfo;
273  
274  
275  // We need to read in new siminfo object.    
276  //parse md file and set up the system
277  //SimCreator NewCreator;
278  SimCreator newCreator;
279  SimInfo* NewInfo = newCreator.createSim(outMdFileName, false);
280  
281  /* create Molocators */
282  locator = new MoLocator(NewInfo->getMoleculeStamp(0), NewInfo->getForceField());
283  
284  
285  
323    Molecule* mol;
287  SimInfo::MoleculeIterator mi;
288  mol = NewInfo->beginMolecule(mi);
324    int l = 0;
325 <  for (mol = NewInfo->beginMolecule(mi); mol != NULL; mol = NewInfo->nextMolecule(mi)) {
326 <    locator->placeMol(latticeSites[l], latticeOrt[l], mol);
327 <    l++;
325 >  for (int i = 0; i < nComponents; i++){
326 >    locator = new MoLocator(newInfo->getMoleculeStamp(i),
327 >                            newInfo->getForceField());
328 >    for (int n = 0; n < nMol.at(i); n++) {
329 >      mol = newInfo->getMoleculeByGlobalIndex(l);
330 >      locator->placeMol(sites[ids[l]], orientations[ids[l]], mol);
331 >      l++;
332 >    }
333    }
334 +  
335 +  // Create DumpWriter and write out the coordinates
336  
337 +  writer = new DumpWriter(newInfo, outputFileName);
338  
296
297  //create dumpwriter and write out the coordinates
298  oldInfo->setFinalConfigFileName(outInitFileName);
299  writer = new DumpWriter(oldInfo);
300
339    if (writer == NULL) {
340 <    std::cerr << "error in creating DumpWriter" << std::endl;
341 <    exit(1);
340 >    sprintf(painCave.errMsg, "error in creating DumpWriter");
341 >    painCave.isFatal = 1;
342 >    simError();
343    }
344  
345    writer->writeDump();
307  std::cout << "new initial configuration file: " << outInitFileName
308            << " is generated." << std::endl;
346  
347 <  //delete objects
347 >  // deleting the writer will put the closing at the end of the dump file.
348  
349 <  //delete oldInfo and oldSimSetup
313 <  if (oldInfo != NULL)
314 <    delete oldInfo;
349 >  delete writer;
350  
351 <  if (writer != NULL)
352 <    delete writer;
353 <    
354 <  delete simpleLat;
320 <
351 >  sprintf(painCave.errMsg, "A new OOPSE MD file called \"%s\" has been "
352 >          "generated.\n", outputFileName.c_str());
353 >  painCave.isFatal = 0;
354 >  simError();
355    return 0;
356   }
357  
358 < void createMdFile(const std::string&oldMdFileName, const std::string&newMdFileName,
359 <                  int components,int* numMol) {
358 > void createMdFile(const std::string&oldMdFileName,
359 >                  const std::string&newMdFileName,
360 >                  std::vector<int> nMol) {
361    ifstream oldMdFile;
362    ofstream newMdFile;
363    const int MAXLEN = 65535;
364    char buffer[MAXLEN];
365    
366    //create new .md file based on old .md file
367 +
368    oldMdFile.open(oldMdFileName.c_str());
369    newMdFile.open(newMdFileName.c_str());
370    
# Line 339 | Line 375 | void createMdFile(const std::string&oldMdFileName, con
375      
376      //correct molecule number
377      if (strstr(buffer, "nMol") != NULL) {
378 <      if(i<components){
379 <        sprintf(buffer, "\tnMol = %i;", numMol[i]);                            
378 >      if(i<nMol.size()){
379 >        sprintf(buffer, "\tnMol = %i;", nMol.at(i));
380          newMdFile << buffer << std::endl;
381          i++;
382        }

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines