Changeset 1bd619 for molecuilder/src/molecules.cpp
- Timestamp:
- Oct 9, 2008, 6:29:34 PM (17 years ago)
- Children:
- 4959f1
- Parents:
- 4a434c
- git-author:
- Frederik Heber <heber@…> (10/09/08 18:27:56)
- git-committer:
- Frederik Heber <heber@…> (10/09/08 18:29:34)
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
molecuilder/src/molecules.cpp
r4a434c r1bd619 2081 2081 int *MinimumRingSize = NULL; 2082 2082 MoleculeLeafClass *Subgraphs = NULL; 2083 class StackClass<bond *> *BackEdgeStack = NULL; 2083 2084 bond *Binder = first; 2084 2085 if ((Binder->next != last) && (Binder->next->Type == Undetermined)) { 2085 2086 *out << Verbose(0) << "No Depth-First-Search analysis performed so far, calling ..." << endl; 2086 Subgraphs = DepthFirstSearchAnalysis(out, MinimumRingSize);2087 Subgraphs = DepthFirstSearchAnalysis(out, BackEdgeStack); 2087 2088 while (Subgraphs->next != NULL) { 2088 2089 Subgraphs = Subgraphs->next; … … 2097 2098 No++; 2098 2099 } 2100 delete(BackEdgeStack); 2099 2101 return No; 2100 2102 }; … … 2178 2180 double *matrix = ReturnFullMatrixforSymmetric(cell_size); 2179 2181 Vector x; 2182 int FalseBondDegree = 0; 2180 2183 2181 2184 BondDistance = bonddistance; // * ((IsAngstroem) ? 1. : 1./AtomicLengthToAngstroem); … … 2196 2199 j += i+1; 2197 2200 divisor[i] = (int)floor(cell_size[j]/bonddistance); // take smaller value such that size of linked cell is at least bonddistance 2198 *out << Verbose(1) << "divisor[" << i << "] = " << divisor[i] << "." << endl;2201 //*out << Verbose(1) << "divisor[" << i << "] = " << divisor[i] << "." << endl; 2199 2202 } 2200 2203 // 2a. allocate memory for the cell list … … 2221 2224 } 2222 2225 index = n[2] + (n[1] + n[0] * divisor[1]) * divisor[2]; 2223 *out << Verbose(1) << "Atom " << *Walker << " goes into cell number [" << n[0] << "," << n[1] << "," << n[2] << "] = " << index << "." << endl;2226 //*out << Verbose(1) << "Atom " << *Walker << " goes into cell number [" << n[0] << "," << n[1] << "," << n[2] << "] = " << index << "." << endl; 2224 2227 // add copy atom to this cell 2225 2228 if (CellList[index] == NULL) // allocate molecule if not done … … 2263 2266 distance = OtherWalker->x.PeriodicDistance(&(Walker->x), cell_size); 2264 2267 if ((OtherWalker->father->nr > Walker->father->nr) && (distance <= MaxDistance*MaxDistance) && (distance >= MinDistance*MinDistance)) { // create bond if distance is smaller 2265 *out << Verbose(0) << "Adding Bond between " << *Walker << " and " << *OtherWalker << "." << endl;2268 //*out << Verbose(0) << "Adding Bond between " << *Walker << " and " << *OtherWalker << "." << endl; 2266 2269 AddBond(Walker->father, OtherWalker->father, 1); // also increases molecule::BondCount 2267 2270 BondCount++; … … 2322 2325 ListOfBondsPerAtom[Walker->nr][CandidateBondNo]->BondDegree++; 2323 2326 *out << Verbose(2) << "Increased bond degree for bond " << *ListOfBondsPerAtom[Walker->nr][CandidateBondNo] << "." << endl; 2324 } 2327 } else 2328 *out << Verbose(2) << "Could not find correct degree for bond " << *ListOfBondsPerAtom[Walker->nr][CandidateBondNo] << "." << endl; 2329 FalseBondDegree++; 2325 2330 } 2326 2331 } … … 2329 2334 } else 2330 2335 *out << Verbose(1) << "BondCount is " << BondCount << ", no bonds between any of the " << AtomCount << " atoms." << endl; 2331 *out << Verbose(1) << "I detected " << BondCount << " bonds in the molecule with distance " << bonddistance << " ." << endl;2336 *out << Verbose(1) << "I detected " << BondCount << " bonds in the molecule with distance " << bonddistance << ", " << FalseBondDegree << " bonds could not be corrected." << endl; 2332 2337 2333 2338 // output bonds for debugging (if bond chain list was correctly installed) … … 2350 2355 * We use the algorithm from [Even, Graph Algorithms, p.62]. 2351 2356 * \param *out output stream for debugging 2352 * \param *& MinimumRingSize contains smallest ring size in molecular structure on return or -1 if no rings were found2357 * \param *&BackEdgeStack NULL pointer to StackClass with all the found back edges, allocated and filled on return 2353 2358 * \return list of each disconnected subgraph as an individual molecule class structure 2354 2359 */ 2355 MoleculeLeafClass * molecule::DepthFirstSearchAnalysis(ofstream *out, int *&MinimumRingSize) 2356 { 2357 class StackClass<atom *> *AtomStack; 2358 AtomStack = new StackClass<atom *>(AtomCount); 2359 class StackClass<bond *> *BackEdgeStack = new StackClass<bond *> (BondCount); 2360 MoleculeLeafClass * molecule::DepthFirstSearchAnalysis(ofstream *out, class StackClass<bond *> *&BackEdgeStack) 2361 { 2362 class StackClass<atom *> *AtomStack = new StackClass<atom *>(AtomCount); 2363 BackEdgeStack = new StackClass<bond *> (BondCount); 2360 2364 MoleculeLeafClass *SubGraphs = new MoleculeLeafClass(NULL); 2361 2365 MoleculeLeafClass *LeafWalker = SubGraphs; … … 2489 2493 LeafWalker->Leaf->Output(out); 2490 2494 *out << endl; 2491 2495 2492 2496 // step on to next root 2493 2497 while ((Root != end) && (Root->GraphNr != -1)) { … … 2507 2511 } 2508 2512 2509 // analysis of the cycles (print rings, get minimum cycle length)2510 CyclicStructureAnalysis(out, BackEdgeStack, MinimumRingSize);2511 2513 2512 2514 *out << Verbose(1) << "Final graph info for each atom is:" << endl; … … 2546 2548 * as cyclic and print out the cycles. 2547 2549 * \param *out output stream for debugging 2548 * \param *BackEdgeStack stack with all back edges found during DFS scan 2550 * \param *BackEdgeStack stack with all back edges found during DFS scan. Beware: This stack contains the bonds from the total molecule, not from the subgraph! 2549 2551 * \param *&MinimumRingSize contains smallest ring size in molecular structure on return or -1 if no rings were found, if set is maximum search distance 2550 2552 * \todo BFS from the not-same-LP to find back to starting point of tributary cycle over more than one bond … … 2567 2569 ColorList[i] = white; 2568 2570 } 2569 MinimumRingSize = new int[AtomCount];2570 for(int i=AtomCount;i--;)2571 MinimumRingSize[i] = AtomCount;2572 2573 2571 2574 2572 *out << Verbose(1) << "Back edge list - "; … … 3372 3370 MoleculeListClass *BondFragments = NULL; 3373 3371 int *SortIndex = NULL; 3374 int *MinimumRingSize = NULL;3372 int *MinimumRingSize = new int[AtomCount]; 3375 3373 int FragmentCounter; 3376 3374 MoleculeLeafClass *MolecularWalker = NULL; … … 3378 3376 fstream File; 3379 3377 bool FragmentationToDo = true; 3378 class StackClass<bond *> *BackEdgeStack = NULL, *LocalBackEdgeStack = NULL; 3380 3379 bool CheckOrder = false; 3381 3380 Graph **FragmentList = NULL; … … 3409 3408 3410 3409 // ===== 2. perform a DFS analysis to gather info on cyclic structure and a list of disconnected subgraphs ===== 3411 Subgraphs = DepthFirstSearchAnalysis(out, MinimumRingSize);3410 Subgraphs = DepthFirstSearchAnalysis(out, BackEdgeStack); 3412 3411 // fill the bond structure of the individually stored subgraphs 3413 3412 Subgraphs->next->FillBondStructureFromReference(out, this, (FragmentCounter = 0), ListOfLocalAtoms, false); // we want to keep the created ListOfLocalAtoms 3414 3413 // analysis of the cycles (print rings, get minimum cycle length) for each subgraph 3414 for(int i=AtomCount;i--;) 3415 MinimumRingSize[i] = AtomCount; 3416 MolecularWalker = Subgraphs; 3417 FragmentCounter = 0; 3418 while (MolecularWalker->next != NULL) { 3419 MolecularWalker = MolecularWalker->next; 3420 *out << Verbose(0) << "Analysing the cycles of subgraph " << MolecularWalker->Leaf << " with nr. " << FragmentCounter << "." << endl; 3421 LocalBackEdgeStack = new StackClass<bond *> (MolecularWalker->Leaf->BondCount); 3422 // // check the list of local atoms for debugging 3423 // *out << Verbose(0) << "ListOfLocalAtoms for this subgraph is:" << endl; 3424 // for (int i=0;i<AtomCount;i++) 3425 // if (ListOfLocalAtoms[FragmentCounter][i] == NULL) 3426 // *out << "\tNULL"; 3427 // else 3428 // *out << "\t" << ListOfLocalAtoms[FragmentCounter][i]->Name; 3429 MolecularWalker->Leaf->PickLocalBackEdges(out, ListOfLocalAtoms[FragmentCounter++], BackEdgeStack, LocalBackEdgeStack); 3430 MolecularWalker->Leaf->CyclicStructureAnalysis(out, LocalBackEdgeStack, MinimumRingSize); 3431 delete(LocalBackEdgeStack); 3432 } 3433 3415 3434 // ===== 3. if structure still valid, parse key set file and others ===== 3416 3435 FragmentationToDo = FragmentationToDo && ParseKeySetFile(out, configuration->configpath, ParsedFragmentList); … … 3421 3440 // =================================== Begin of FRAGMENTATION =============================== 3422 3441 // ===== 6a. assign each keyset to its respective subgraph ===== 3423 Subgraphs->next->AssignKeySetsToFragment(out, this, ParsedFragmentList, ListOfLocalAtoms, FragmentList, (FragmentCounter = 0), false);3442 Subgraphs->next->AssignKeySetsToFragment(out, this, ParsedFragmentList, ListOfLocalAtoms, FragmentList, (FragmentCounter = 0), true); 3424 3443 3425 3444 // ===== 6b. prepare and go into the adaptive (Order<0), single-step (Order==0) or incremental (Order>0) cycle … … 3458 3477 delete[](MinimumRingSize); 3459 3478 3460 // free the index lookup list3461 for (int i=FragmentCounter;i--;)3462 Free((void **)&ListOfLocalAtoms[i], "molecule::FragmentMolecule - *ListOfLocalAtoms[]");3463 Free((void **)&ListOfLocalAtoms, "molecule::FragmentMolecule - **ListOfLocalAtoms");3464 3479 3465 3480 // ==================================== End of FRAGMENTATION ============================================ … … 3535 3550 }; 3536 3551 3552 3553 /** Picks from a global stack with all back edges the ones in the fragment. 3554 * \param *out output stream for debugging 3555 * \param **ListOfLocalAtoms array of father atom::nr to local atom::nr (reverse of atom::father) 3556 * \param *ReferenceStack stack with all the back egdes 3557 * \param *LocalStack stack to be filled 3558 * \return true - everything ok, false - ReferenceStack was empty 3559 */ 3560 bool molecule::PickLocalBackEdges(ofstream *out, atom **ListOfLocalAtoms, class StackClass<bond *> *&ReferenceStack, class StackClass<bond *> *&LocalStack) 3561 { 3562 bool status = true; 3563 if (ReferenceStack->IsEmpty()) { 3564 cerr << "ReferenceStack is empty!" << endl; 3565 return false; 3566 } 3567 bond *Binder = ReferenceStack->PopFirst(); 3568 bond *FirstBond = Binder; // mark the first bond, so that we don't loop through the stack indefinitely 3569 atom *Walker = NULL, *OtherAtom = NULL; 3570 ReferenceStack->Push(Binder); 3571 3572 do { // go through all bonds and push local ones 3573 Walker = ListOfLocalAtoms[Binder->leftatom->nr]; // get one atom in the reference molecule 3574 if (Walker == NULL) // if this Walker exists in the subgraph ... 3575 continue; 3576 for(int i=0;i<NumberOfBondsPerAtom[Walker->nr];i++) { // go through the local list of bonds 3577 OtherAtom = ListOfBondsPerAtom[Walker->nr][i]->GetOtherAtom(Walker); 3578 if (OtherAtom == ListOfLocalAtoms[Binder->rightatom->nr]) { // found the bond 3579 LocalStack->Push(ListOfBondsPerAtom[Walker->nr][i]); 3580 break; 3581 } 3582 } 3583 Binder = ReferenceStack->PopFirst(); // loop the stack for next item 3584 ReferenceStack->Push(Binder); 3585 } while (FirstBond != Binder); 3586 3587 return status; 3588 }; 3589 3537 3590 /** Stores pairs (Atom::nr, Atom::AdaptiveOrder) into file. 3538 3591 * Atoms not present in the file get "-1". … … 3677 3730 while (Walker->next != end) { 3678 3731 Walker = Walker->next; 3679 *out << Verbose(4) << "Atom " << Walker->Name << " with " << NumberOfBondsPerAtom[Walker->nr] << " bonds: ";3732 *out << Verbose(4) << "Atom " << Walker->Name << "/" << Walker->nr << " with " << NumberOfBondsPerAtom[Walker->nr] << " bonds: "; 3680 3733 TotalDegree = 0; 3681 3734 for (int j=0;j<NumberOfBondsPerAtom[Walker->nr];j++) {
Note:
See TracChangeset
for help on using the changeset viewer.