source: molecuilder/src/parser.cpp@ 30fda2

Last change on this file since 30fda2 was c75363, checked in by Frederik Heber <heber@…>, 17 years ago

HUGE REWRITE to allow for adaptive increase of the bond order, first working commit

Lots of code was thrown out:
-BottomUp, TopDown and GetAtomicFragments
-TEFactors are now used as "CreationCounters", i.e. the count how often a fragment as been created (ideal would be only once)
-ReduceToUniqueOnes and stuff all thrown out, since they are out-dated since use of hash table
Other changes:
-CreateListofUniqueFragments renamed to PowerSetGenerator
-PowerSetGenerator goes not over all reachable roots, but one given by calling function FragmentBOSSANOVA
-FragmentBOSSANOVA loops over all possible root sites and hands this over to PowerSetGenerator
-by the virtue of the hash table it is not important anymore whether created keysets are unique or not, as this is recognized in log(n). Hence, the label < label is not important anymore (and not applicable in an adaptive scheme with old, parsed keysets and unknown labels) (THIS IS HOWEVER NOT DONE YET!)
The setup is then as follows:

  1. FragmentMolecule
    1. parses adjacency, keysets and orderatsite files
    2. performs DFS to find connected subgraphs (to leave this in was a design decision: might be useful later)
    3. a RootStack is created for every subgraph (here, later we implement the "update 10 sites with highest energy contribution", and that's why this consciously not done in the following loop)
    4. in a loop over all subgraphs

d1. calls FragmentBOSSANOVA with this RootStack and within the subgraph molecule structure
d2. creates molecule (fragment)s from the returned keysets (StoreFragmentFromKeySet)

  1. combines the generated molecule lists from all subgraphs
  2. saves to disk: fragment configs, adjacency, orderatsite, keyset files
  1. FragmentBOSSANOVA
    1. constructs a complete keyset of the molecule
    2. In a loop over all possible roots from the given rootstack

b1. increases order of root site
b2. calls PowerSetGenerator with this order, the complete keyset and the rootkeynr
b3. for all consecutive lower levels PowerSetGenerator is called with the suborder, the higher order keyset as the restricted one and each site in the set as the root)
b4. these are merged into a fragment list of keysets

  1. All fragment lists (for all orders, i.e. from all destination fields) are merged into one list for return
  1. PowerSetGenerator
    1. initialises UniqueFragments structure
    2. fills edge list via BFS
    3. creates the fragment by calling recursive function SPFragmentGenerator with UniqueFragments structure, 0 as root distance, the edge set, its dimension and the current suborder
    4. Free'ing structure
  2. SPFragmentGenerator (nothing much has changed here)
    1. loops over every possible combination (2dimension of edge set)

a1. inserts current set, if there's still space left

a11. yes: calls SPFragmentGenerator with structure, created new edge list and size respective to root distance+1
a12. no: stores fragment into keyset list by calling InsertFragmentIntoGraph

a2. removes all items added into the snake stack (in UniqueFragments structure) added during level (root distance) and current set

  • Property mode set to 100644
File size: 23.1 KB
Line 
1/** \file parsing.cpp
2 *
3 * Declarations of various class functions for the parsing of value files.
4 *
5 */
6
7// ======================================= INCLUDES ==========================================
8
9#include "helpers.hpp"
10#include "parser.hpp"
11
12// ======================================= FUNCTIONS ==========================================
13
14/** Test if given filename can be opened.
15 * \param filename name of file
16 * \return given file exists
17 */
18#ifdef HAVE_INLINE
19inline bool FilePresent(const char *filename)
20#else
21bool FilePresent(const char *filename)
22#endif
23{
24 ifstream input;
25
26 input.open(filename, ios::in);
27 if (input == NULL) {
28 cout << endl << "Unable to open " << filename << ", is the directory correct?" << endl;
29 return false;
30 }
31 input.close();
32 return true;
33};
34
35/** Test the given parameters.
36 * \param argc argument count
37 * \param **argv arguments array
38 * \return given inputdir is valid
39 */
40bool TestParams(int argc, char **argv)
41{
42 ifstream input;
43 stringstream line;
44
45 //line << argv[1] << FRAGMENTPREFIX << TEFACTORSFILE;
46 return FilePresent(line.str().c_str());
47};
48
49// ======================================= CLASS MatrixContainer =============================
50
51/** Constructor of MatrixContainer class.
52 */
53MatrixContainer::MatrixContainer() {
54 Matrix = NULL;
55 Indices = NULL;
56 Header = NULL;
57 MatrixCounter = 0;
58 RowCounter = NULL;
59 ColumnCounter = 0;
60};
61
62/** Destructor of MatrixContainer class.
63 */
64MatrixContainer::~MatrixContainer() {
65 if (Matrix != NULL)
66 for(int i=0;i<MatrixCounter;i++) {
67 if (RowCounter != NULL)
68 for(int j=0;j<=RowCounter[i];j++)
69 Free((void **)&Matrix[i][j], "MatrixContainer::~MatrixContainer: *Matrix[][]");
70 Free((void **)&Matrix[i], "MatrixContainer::~MatrixContainer: **Matrix[]");
71 }
72 if ((RowCounter != NULL) && (Matrix[MatrixCounter] != NULL))
73 for(int j=0;j<=RowCounter[MatrixCounter];j++)
74 Free((void **)&Matrix[MatrixCounter][j], "MatrixContainer::~MatrixContainer: *Matrix[MatrixCounter][]");
75 Free((void **)&Matrix[MatrixCounter], "MatrixContainer::~MatrixContainer: **Matrix[MatrixCounter]");
76 Free((void **)&Matrix, "MatrixContainer::~MatrixContainer: ***Matrix");
77
78 if (Indices != NULL)
79 for(int i=0;i<=MatrixCounter;i++) {
80 Free((void **)&Indices[i], "MatrixContainer::~MatrixContainer: *Indices[]");
81 }
82 Free((void **)&Indices, "MatrixContainer::~MatrixContainer: **Indices");
83
84 Free((void **)&Header, "MatrixContainer::~MatrixContainer: *Header");
85 Free((void **)&RowCounter, "MatrixContainer::~MatrixContainer: *RowCounter");
86};
87
88/** Parsing a number of matrices.
89 * \param *name directory with files
90 * \param *prefix prefix of each matrix file
91 * \param *suffix suffix of each matrix file
92 * \param skiplines number of inital lines to skip
93 * \param skiplines number of inital columns to skip
94 * \return parsing successful
95 */
96bool MatrixContainer::ParseMatrix(char *name, char *prefix, char *suffix, int skiplines, int skipcolumns)
97{
98 char filename[1023];
99 ifstream input;
100 char *FragmentNumber = NULL;
101 stringstream line;
102 double tmp;
103
104 Header = (char *) Malloc(sizeof(char)*1023, "MatrixContainer::ParseMatrix: *EnergyHeader");
105
106 // count the number of matrices
107 MatrixCounter = -1; // we count one too much
108 line << name << FRAGMENTPREFIX << KEYSETFILE;
109 input.open(line.str().c_str(), ios::in);
110 if (input == NULL) {
111 cout << endl << "Unable to open " << line.str() << ", is the directory correct?" << endl;
112 return false;
113 }
114 while (!input.eof()) {
115 input >> tmp;
116 MatrixCounter++;
117 }
118 input.close();
119 cout << "Determined " << MatrixCounter << " fragments." << endl;
120
121 cout << "Parsing through each fragment and retrieving " << prefix << suffix << "." << endl;
122 Matrix = (double ***) Malloc(sizeof(double **)*(MatrixCounter+1), "MatrixContainer::ParseMatrix: ***Matrix"); // one more each for the total molecule
123 RowCounter = (int *) Malloc(sizeof(int)*(MatrixCounter+1), "MatrixContainer::ParseMatrix: *RowCounter");
124 for(int i=0;i<=MatrixCounter;i++) {
125 // energy
126 stringstream line;
127 FragmentNumber = FixedDigitNumber(MatrixCounter, i);
128 if (i != MatrixCounter)
129 line << name << FRAGMENTPREFIX << FragmentNumber << "/" << prefix << suffix;
130 else
131 line << name << prefix << suffix;
132 Free((void **)&FragmentNumber, "MatrixContainer::ParseMatrix: *FragmentNumber");
133 input.open(line.str().c_str(), ios::in);
134 //cout << "Opening " << line.str() << " ... " << input << endl;
135 if (input == NULL) {
136 cerr << endl << "Unable to open " << line.str() << ", is the directory correct?" << endl;
137 return false;
138 }
139 // scan header for number of columns
140 for (int m=0;m<=skiplines;m++)
141 input.getline(Header, 1023);
142 line.str(Header);
143 for(int k=0;k<skipcolumns;k++)
144 line >> Header;
145 //cout << line.str() << endl;
146 ColumnCounter=0;
147 while (!line.eof()) {
148 strcpy(filename,"@");
149 line >> filename;
150 if (filename[0] != '@')
151 ColumnCounter++;
152 }
153 //cout << line.str() << endl;
154 //cout << "ColumnCounter: " << ColumnCounter << endl;
155 // scan rest for number of rows/lines
156 RowCounter[i]=-1; // counts one line too much
157 while (!input.eof()) {
158 input.getline(filename, 1023);
159 //cout << "Comparing: " << strncmp(filename,"MeanForce",9) << endl;
160 RowCounter[i]++; // then line was not last MeanForce
161 if (strncmp(filename,"MeanForce", 9) == 0) {
162 break;
163 }
164 }
165 cout << "RowCounter[" << i << "]: " << RowCounter[i] << endl;
166 Matrix[i] = (double **) Malloc(sizeof(double *)*(RowCounter[i]+1), "MatrixContainer::ParseMatrix: **Matrix[]");
167 input.clear();
168 input.seekg(ios::beg);
169 for (int m=0;m<=skiplines;m++)
170 input.getline(Header, 1023); // skip header
171 line.str(Header);
172 for(int k=0;k<skipcolumns;k++) // skip columns in header too
173 line >> filename;
174 strncpy(Header, line.str().c_str(), 1023);
175 for(int j=0;j<RowCounter[i];j++) {
176 Matrix[i][j] = (double *) Malloc(sizeof(double)*ColumnCounter, "MatrixContainer::ParseMatrix: *Matrix[][]");
177 input.getline(filename, 1023);
178 stringstream line(filename);
179 //cout << "Matrix at level " << j << ":";// << filename << endl;
180 for(int k=0;k<skipcolumns;k++)
181 line >> filename;
182 for(int k=0;(k<ColumnCounter) && (!line.eof());k++) {
183 line >> Matrix[i][j][k];
184 //cout << " " << setprecision(2) << Matrix[i][j][k];;
185 }
186 //cout << endl;
187 }
188 Matrix[i][ RowCounter[i] ] = (double *) Malloc(sizeof(double)*ColumnCounter, "MatrixContainer::ParseMatrix: *Matrix[RowCounter[i]][]");
189 for(int j=0;j<ColumnCounter;j++)
190 Matrix[i][ RowCounter[i] ][j] = 0.;
191 input.close();
192 }
193 return true;
194};
195
196/** Allocates and resets the memory for a number \a MCounter of matrices.
197 * \param *GivenHeader Header line
198 * \param MCounter number of matrices
199 * \param *RCounter number of rows for each matrix
200 * \param CCounter number of columns for all matrices
201 * \return Allocation successful
202 */
203bool MatrixContainer::AllocateMatrix(char *GivenHeader, int MCounter, int *RCounter, int CCounter)
204{
205 Header = (char *) Malloc(sizeof(char)*1024, "MatrixContainer::ParseMatrix: *EnergyHeader");
206 strncpy(Header, GivenHeader, 1023);
207
208 MatrixCounter = MCounter;
209 ColumnCounter = CCounter;
210 Matrix = (double ***) Malloc(sizeof(double **)*(MatrixCounter+1), "MatrixContainer::ParseMatrix: ***Matrix"); // one more each for the total molecule
211 RowCounter = (int *) Malloc(sizeof(int)*(MatrixCounter+1), "MatrixContainer::ParseMatrix: *RowCounter");
212 for(int i=0;i<=MatrixCounter;i++) {
213 RowCounter[i] = RCounter[i];
214 Matrix[i] = (double **) Malloc(sizeof(double *)*(RowCounter[i]+1), "MatrixContainer::ParseMatrix: **Matrix[]");
215 for(int j=0;j<=RowCounter[i];j++) {
216 Matrix[i][j] = (double *) Malloc(sizeof(double)*ColumnCounter, "MatrixContainer::ParseMatrix: *Matrix[][]");
217 for(int k=0;k<ColumnCounter;k++)
218 Matrix[i][j][k] = 0.;
219 }
220 }
221 return true;
222};
223
224/** Resets all values in MatrixContainer::Matrix.
225 * \return true if successful
226 */
227bool MatrixContainer::ResetMatrix()
228{
229 for(int i=0;i<=MatrixCounter;i++)
230 for(int j=0;j<=RowCounter[i];j++)
231 for(int k=0;k<ColumnCounter;k++)
232 Matrix[i][j][k] = 0.;
233 return true;
234};
235
236/** Sets all values in the last of MatrixContainer::Matrix to \a value.
237 * \param value reset value
238 * \param skipcolumns skip initial columns
239 * \return true if successful
240 */
241bool MatrixContainer::SetLastMatrix(double value, int skipcolumns)
242{
243 for(int j=0;j<=RowCounter[MatrixCounter];j++)
244 for(int k=skipcolumns;k<ColumnCounter;k++)
245 Matrix[MatrixCounter][j][k] = value;
246 return true;
247};
248
249/** Sets all values in the last of MatrixContainer::Matrix to \a value.
250 * \param **values matrix with each value (must have at least same dimensions!)
251 * \param skipcolumns skip initial columns
252 * \return true if successful
253 */
254bool MatrixContainer::SetLastMatrix(double **values, int skipcolumns)
255{
256 for(int j=0;j<=RowCounter[MatrixCounter];j++)
257 for(int k=skipcolumns;k<ColumnCounter;k++)
258 Matrix[MatrixCounter][j][k] = values[j][k];
259 return true;
260};
261
262/** Sums the energy with each factor and put into last element of \a ***Energies.
263 * \param Matrix MatrixContainer with matrices (LevelCounter by ColumnCounter) with all the energies.
264 * \param KeySet KeySetContainer with bond Order and association mapping of each fragment to an order
265 * \param Order bond order
266 * \return true if summing was successful
267 */
268bool MatrixContainer::SumSubManyBodyTerms(class MatrixContainer &MatrixValues, class KeySetsContainer &KeySet, int Order)
269{
270 // go through each order
271 for (int CurrentFragment=0;CurrentFragment<KeySet.FragmentsPerOrder[Order];CurrentFragment++) {
272 //cout << "Current Fragment is " << CurrentFragment << "/" << KeySet.OrderSet[Order][CurrentFragment] << "." << endl;
273 // then go per order through each suborder and pick together all the terms that contain this fragment
274 for(int SubOrder=0;SubOrder<=Order;SubOrder++) { // go through all suborders up to the desired order
275 for (int j=0;j<KeySet.FragmentsPerOrder[SubOrder];j++) { // go through all possible fragments of size suborder
276 if (KeySet.Contains(KeySet.OrderSet[Order][CurrentFragment], KeySet.OrderSet[SubOrder][j])) {
277 //cout << "Current other fragment is " << j << "/" << KeySet.OrderSet[SubOrder][j] << "." << endl;
278 // if the fragment's indices are all in the current fragment
279 for(int k=0;k<RowCounter[ KeySet.OrderSet[SubOrder][j] ];k++) { // go through all atoms in this fragment
280 int m = MatrixValues.Indices[ KeySet.OrderSet[SubOrder][j] ][k];
281 //cout << "Current index is " << k << "/" << m << "." << endl;
282 if (m != -1) { // if it's not an added hydrogen
283 for (int l=0;l<RowCounter[ KeySet.OrderSet[Order][CurrentFragment] ];l++) { // look for the corresponding index in the current fragment
284 //cout << "Comparing " << m << " with " << Matrix.Indices[ KeySet.OrderSet[Order][CurrentFragment] ][l] << "." << endl;
285 if (m == MatrixValues.Indices[ KeySet.OrderSet[Order][CurrentFragment] ][l]) {
286 m = l;
287 break;
288 }
289 }
290 //cout << "Corresponding index in CurrentFragment is " << m << "." << endl;
291 if (m > RowCounter[ KeySet.OrderSet[Order][CurrentFragment] ]) {
292 cerr << "Current force index " << m << " is greater than " << RowCounter[ KeySet.OrderSet[Order][CurrentFragment] ] << "!" << endl;
293 return false;
294 }
295 if (Order == SubOrder) { // equal order is always copy from Energies
296 for(int l=0;l<ColumnCounter;l++) // then adds/subtract each column
297 Matrix[ KeySet.OrderSet[Order][CurrentFragment] ][m][l] += MatrixValues.Matrix[ KeySet.OrderSet[SubOrder][j] ][k][l];
298 } else {
299 for(int l=0;l<ColumnCounter;l++)
300 Matrix[ KeySet.OrderSet[Order][CurrentFragment] ][m][l] -= Matrix[ KeySet.OrderSet[SubOrder][j] ][k][l];
301 }
302 }
303 //if ((ColumnCounter>1) && (RowCounter >= 1))
304 //cout << "Fragments[ KeySet.OrderSet[" << i << "][" << CurrentFragment << "]=" << KeySet.OrderSet[Order][CurrentFragment] << " ][" << RowCounter[0]-1 << "][" << 1 << "] = " << Fragments[ KeySet.OrderSet[Order][CurrentFragment] ][RowCounter[0]-1][1] << endl;
305 }
306 } else {
307 //cout << "Fragment " << KeySet.OrderSet[SubOrder][j] << " is not contained in fragment " << KeySet. KeySet.OrderSet[Order][CurrentFragment] << "." << endl;
308 }
309 }
310 }
311 //cout << "Final Fragments[ KeySet.OrderSet[" << Order << "][" << CurrentFragment << "]=" << KeySet.OrderSet[Order][CurrentFragment] << " ][" << KeySet.AtomCounter[0]-1 << "][" << 1 << "] = " << Fragments[ KeySet.OrderSet[Order][CurrentFragment] ][KeySet.AtomCounter[0]-1][1] << endl;
312 }
313
314 return true;
315};
316
317/** Writes the summed total fragment terms \f$F_{ij}\f$ to file.
318 * \param *name inputdir
319 * \param *prefix prefix before \a EnergySuffix
320 * \return file was written
321 */
322bool MatrixContainer::WriteTotalFragments(const char *name, const char *prefix)
323{
324 ofstream output;
325 char *FragmentNumber = NULL;
326
327 cout << "Writing fragment files." << endl;
328 for(int i=0;i<MatrixCounter;i++) {
329 stringstream line;
330 FragmentNumber = FixedDigitNumber(MatrixCounter, i);
331 line << name << FRAGMENTPREFIX << FragmentNumber << "/" << prefix;
332 Free((void **)&FragmentNumber, "*FragmentNumber");
333 output.open(line.str().c_str(), ios::out);
334 if (output == NULL) {
335 cerr << "Unable to open output energy file " << line.str() << "!" << endl;
336 return false;
337 }
338 output << Header << endl;
339 for(int j=0;j<RowCounter[i];j++) {
340 for(int k=0;k<ColumnCounter;k++)
341 output << scientific << Matrix[i][j][k] << "\t";
342 output << endl;
343 }
344 output.close();
345 }
346 return true;
347};
348
349/** Writes the summed total values in the last matrix to file.
350 * \param *name inputdir
351 * \param *prefix prefix
352 * \param *suffix suffix
353 * \return file was written
354 */
355bool MatrixContainer::WriteLastMatrix(const char *name, const char *prefix, const char *suffix)
356{
357 ofstream output;
358 stringstream line;
359
360 cout << "Writing matrix values of " << suffix << "." << endl;
361 line << name << prefix << suffix;
362 output.open(line.str().c_str(), ios::out);
363 if (output == NULL) {
364 cerr << "Unable to open output matrix file " << line.str() << "!" << endl;
365 return false;
366 }
367 output << Header << endl;
368 for(int j=0;j<RowCounter[MatrixCounter];j++) {
369 for(int k=0;k<ColumnCounter;k++)
370 output << scientific << Matrix[MatrixCounter][j][k] << "\t";
371 output << endl;
372 }
373 output.close();
374 return true;
375};
376
377// ======================================= CLASS EnergyMatrix =============================
378
379/** Create a trivial energy index mapping.
380 * This just maps 1 to 1, 2 to 2 and so on for all fragments.
381 * \return creation sucessful
382 */
383bool EnergyMatrix::ParseIndices()
384{
385 cout << "Parsing energy indices." << endl;
386 Indices = (int **) Malloc(sizeof(int *)*(MatrixCounter+1), "EnergyMatrix::ParseIndices: **Indices");
387 for(int i=0;i<=MatrixCounter;i++) {
388 Indices[i] = (int *) Malloc(sizeof(int)*RowCounter[i], "EnergyMatrix::ParseIndices: *Indices[]");
389 for(int j=0;j<RowCounter[i];j++)
390 Indices[i][j] = j;
391 }
392 return true;
393};
394
395/** Sums the energy with each factor and put into last element of \a EnergyMatrix::Matrix.
396 * \param Matrix MatrixContainer with matrices (LevelCounter by ColumnCounter) with all the energies.
397 * \param KeySet KeySetContainer with bond Order and association mapping of each fragment to an order
398 * \param Order bond order
399 * \return true if summing was successful
400 */
401bool EnergyMatrix::SumSubEnergy(class EnergyMatrix &Fragments, class KeySetsContainer &KeySet, int Order)
402{
403 // sum energy
404 for(int i=0;i<KeySet.FragmentsPerOrder[Order];i++)
405 for(int j=0;j<RowCounter[ KeySet.OrderSet[Order][i] ];j++)
406 for(int k=0;k<ColumnCounter;k++)
407 Matrix[MatrixCounter][j][k] += Fragments.Matrix[ KeySet.OrderSet[Order][i] ][j][k];
408 return true;
409};
410
411// ======================================= CLASS ForceMatrix =============================
412
413/** Parsing force Indices of each fragment
414 * \param *name directory with \a ForcesFile
415 * \return parsing successful
416 */
417bool ForceMatrix::ParseIndices(char *name)
418{
419 cout << "Parsing force indices." << endl;
420 Indices = (int **) Malloc(sizeof(int *)*(MatrixCounter+1), "ForceMatrix::ParseIndices: **Indices");
421 for (int i=0;i<MatrixCounter;i++) {
422 Indices[i] = (int *) Malloc(sizeof(int)*RowCounter[i], "ForceMatrix::ParseIndices: *Indices[]");
423 for(int j=0;j<RowCounter[i];j++)
424 Indices[i][j] = j;
425 }
426 Indices[MatrixCounter] = (int *) Malloc(sizeof(int)*RowCounter[MatrixCounter], "ForceMatrix::ParseIndices: *Indices[]");
427 for(int j=0;j<RowCounter[MatrixCounter];j++) {
428 Indices[MatrixCounter][j] = j;
429 }
430 return true;
431};
432
433
434/** Sums the forces and puts into last element of \a ForceMatrix::Matrix.
435 * \param Matrix MatrixContainer with matrices (LevelCounter by ColumnCounter) with all the energies.
436 * \param KeySet KeySetContainer with bond Order and association mapping of each fragment to an order
437 * \param Order bond order
438 * \return true if summing was successful
439 */
440bool ForceMatrix::SumSubForces(class ForceMatrix &Fragments, class KeySetsContainer &KeySet, int Order)
441{
442 // sum forces
443 for(int i=0;i<KeySet.FragmentsPerOrder[Order];i++)
444 for(int l=0;l<RowCounter[ KeySet.OrderSet[Order][i] ];l++) {
445 int j = Indices[ KeySet.OrderSet[Order][i] ][l];
446 if (j > RowCounter[MatrixCounter]) {
447 cerr << "Current force index " << j << " is greater than " << RowCounter[MatrixCounter] << "!" << endl;
448 return false;
449 }
450 if (j != -1)
451 for(int k=2;k<ColumnCounter;k++)
452 Matrix[MatrixCounter][j][k] += Fragments.Matrix[ KeySet.OrderSet[Order][i] ][l][k];
453 }
454 return true;
455};
456
457
458// ======================================= CLASS KeySetsContainer =============================
459
460/** Constructor of KeySetsContainer class.
461 */
462KeySetsContainer::KeySetsContainer() {
463 KeySets = NULL;
464 AtomCounter = NULL;
465 FragmentCounter = 0;
466 Order = 0;
467 FragmentsPerOrder = 0;
468 OrderSet = NULL;
469};
470
471/** Destructor of KeySetsContainer class.
472 */
473KeySetsContainer::~KeySetsContainer() {
474 for(int i=0;i<FragmentCounter;i++)
475 Free((void **)&KeySets[i], "KeySetsContainer::~KeySetsContainer: *KeySets[]");
476 for(int i=0;i<Order;i++)
477 Free((void **)&OrderSet[i], "KeySetsContainer::~KeySetsContainer: *OrderSet[]");
478 Free((void **)&KeySets, "KeySetsContainer::~KeySetsContainer: **KeySets");
479 Free((void **)&OrderSet, "KeySetsContainer::~KeySetsContainer: **OrderSet");
480 Free((void **)&AtomCounter, "KeySetsContainer::~KeySetsContainer: *AtomCounter");
481 Free((void **)&FragmentsPerOrder, "KeySetsContainer::~KeySetsContainer: *FragmentsPerOrder");
482};
483
484/** Parsing KeySets into array.
485 * \param *name directory with keyset file
486 * \param *ACounter number of atoms per fragment
487 * \param FCounter number of fragments
488 * \return parsing succesful
489 */
490bool KeySetsContainer::ParseKeySets(const char *name, const int *ACounter, const int FCounter) {
491 ifstream input;
492 char *FragmentNumber = NULL;
493 stringstream line;
494 char filename[1023];
495
496 FragmentCounter = FCounter;
497 cout << "Parsing key sets." << endl;
498 KeySets = (int **) Malloc(sizeof(int *)*FragmentCounter, "KeySetsContainer::ParseKeySets: **KeySets");
499 line << name << FRAGMENTPREFIX << KEYSETFILE;
500 input.open(line.str().c_str(), ios::in);
501 if (input == NULL) {
502 cout << endl << "Unable to open " << line.str() << ", is the directory correct?" << endl;
503 return false;
504 }
505
506 AtomCounter = (int *) Malloc(sizeof(int)*FragmentCounter, "KeySetsContainer::ParseKeySets: *RowCounter");
507 for(int i=0;(i<FragmentCounter) && (!input.eof());i++) {
508 stringstream line;
509 AtomCounter[i] = ACounter[i];
510 // parse the values
511 KeySets[i] = (int *) Malloc(sizeof(int)*AtomCounter[i], "KeySetsContainer::ParseKeySets: *KeySets[]");
512 FragmentNumber = FixedDigitNumber(FragmentCounter, i);
513 cout << FRAGMENTPREFIX << FragmentNumber << "[" << AtomCounter[i] << "]:";
514 Free((void **)&FragmentNumber, "KeySetsContainer::ParseKeySets: *FragmentNumber");
515 input.getline(filename, 1023);
516 line.str(filename);
517 for(int j=0;(j<AtomCounter[i]) && (!line.eof());j++) {
518 line >> KeySets[i][j];
519 cout << " " << KeySets[i][j];
520 }
521 cout << endl;
522 }
523 input.close();
524 return true;
525};
526
527/** Parse many body terms, associating each fragment to a certain bond order.
528 * \return parsing succesful
529 */
530bool KeySetsContainer::ParseManyBodyTerms()
531{
532 int Counter;
533
534 cout << "Creating Fragment terms." << endl;
535 // scan through all to determine order
536 Order=0;
537 for(int i=0;i<FragmentCounter;i++) {
538 Counter=0;
539 for(int j=0;j<AtomCounter[i];j++)
540 if (KeySets[i][j] != -1)
541 Counter++;
542 if (Counter > Order)
543 Order = Counter;
544 }
545 cout << "Found Order is " << Order << "." << endl;
546
547 // scan through all to determine fragments per order
548 FragmentsPerOrder = (int *) Malloc(sizeof(int)*Order, "KeySetsContainer::ParseManyBodyTerms: *FragmentsPerOrder");
549 for(int i=0;i<Order;i++)
550 FragmentsPerOrder[i] = 0;
551 for(int i=0;i<FragmentCounter;i++) {
552 Counter=0;
553 for(int j=0;j<AtomCounter[i];j++)
554 if (KeySets[i][j] != -1)
555 Counter++;
556 FragmentsPerOrder[Counter-1]++;
557 }
558 for(int i=0;i<Order;i++)
559 cout << "Found No. of Fragments of Order " << i+1 << " is " << FragmentsPerOrder[i] << "." << endl;
560
561 // scan through all to gather indices to each order set
562 OrderSet = (int **) Malloc(sizeof(int *)*Order, "KeySetsContainer::ParseManyBodyTerms: **OrderSet");
563 for(int i=0;i<Order;i++)
564 OrderSet[i] = (int *) Malloc(sizeof(int)*FragmentsPerOrder[i], "KeySetsContainer::ParseManyBodyTermsKeySetsContainer::ParseManyBodyTerms: *OrderSet[]");
565 for(int i=0;i<Order;i++)
566 FragmentsPerOrder[i] = 0;
567 for(int i=0;i<FragmentCounter;i++) {
568 Counter=0;
569 for(int j=0;j<AtomCounter[i];j++)
570 if (KeySets[i][j] != -1)
571 Counter++;
572 OrderSet[Counter-1][FragmentsPerOrder[Counter-1]] = i;
573 FragmentsPerOrder[Counter-1]++;
574 }
575 cout << "Printing OrderSet." << endl;
576 for(int i=0;i<Order;i++) {
577 for (int j=0;j<FragmentsPerOrder[i];j++) {
578 cout << " " << OrderSet[i][j];
579 }
580 cout << endl;
581 }
582 cout << endl;
583
584
585 return true;
586};
587
588/** Compares each entry in \a *SmallerSet if it is containted in \a *GreaterSet.
589 * \param GreaterSet index to greater set
590 * \param SmallerSet index to smaller set
591 * \return true if all keys of SmallerSet contained in GreaterSet
592 */
593bool KeySetsContainer::Contains(const int GreaterSet, const int SmallerSet)
594{
595 bool result = true;
596 bool intermediate;
597 if ((GreaterSet < 0) || (SmallerSet < 0) || (GreaterSet > FragmentCounter) || (SmallerSet > FragmentCounter)) // index out of bounds
598 return false;
599 for(int i=0;i<AtomCounter[SmallerSet];i++) {
600 intermediate = false;
601 for (int j=0;j<AtomCounter[GreaterSet];j++)
602 intermediate = (intermediate || ((KeySets[SmallerSet][i] == KeySets[GreaterSet][j]) || (KeySets[SmallerSet][i] == -1)));
603 result = result && intermediate;
604 }
605
606 return result;
607};
608
609
610// ======================================= END =============================================
Note: See TracBrowser for help on using the repository browser.