Geant4 Cross Reference |
1 // 1 2 // ******************************************* 3 // * License and Disclaimer 4 // * 5 // * The Geant4 software is copyright of th 6 // * the Geant4 Collaboration. It is provided 7 // * conditions of the Geant4 Software License 8 // * LICENSE and available at http://cern.ch/ 9 // * include a list of copyright holders. 10 // * 11 // * Neither the authors of this software syst 12 // * institutes,nor the agencies providing fin 13 // * work make any representation or warran 14 // * regarding this software system or assum 15 // * use. Please see the license in the file 16 // * for the full disclaimer and the limitatio 17 // * 18 // * This code implementation is the result 19 // * technical work of the GEANT4 collaboratio 20 // * By using, copying, modifying or distri 21 // * any work based on the software) you ag 22 // * use in resulting scientific publicati 23 // * acceptance of all terms of the Geant4 Sof 24 // ******************************************* 25 // 26 // 27 // Author: Mathieu Karamitros (kara (AT) cenbg 28 // 29 // History: 30 // ----------- 31 // 10 Oct 2011 M.Karamitros created 32 // 33 // ------------------------------------------- 34 35 #include "G4MolecularConfiguration.hh" 36 #include "G4MoleculeDefinition.hh" 37 #include "G4UIcommand.hh" 38 #include "G4AllocatorList.hh" 39 #include "G4AutoLock.hh" 40 #include "G4MoleculeTable.hh" 41 #include "G4Serialize.hh" 42 #include <fstream> 43 44 using CLHEP::m2; 45 using CLHEP::s; 46 using CLHEP::kelvin; 47 48 using namespace std; 49 50 #if defined ( WIN32 ) 51 #define __func__ __FUNCTION__ 52 #endif 53 54 /*G4ThreadLocal*/G4double G4MolecularConfigura 55 // 25°C, used to shoot an energy 56 57 //____________________________________________ 58 // G4MolecularConfigurationManager 59 using MolecularConfigurationManager = G4Molecu 60 61 MolecularConfigurationManager* G4MolecularConf 62 63 G4Mutex MolecularConfigurationManager::fManage 64 65 int G4MolecularConfiguration::GetNumberOfSpeci 66 { 67 return GetManager()->GetNumberOfCreatedSpeci 68 } 69 70 double G4MolecularConfiguration::ReturnDefault 71 double, 72 const G4M 73 molConf) 74 { 75 return molConf->fDynDiffusionCoefficient; 76 } 77 78 G4MolecularConfiguration::G4MolecularConfigura 79 80 81 { 82 fMoleculeDefinition = moleculeDef; 83 84 fLabel = new G4String(label); 85 86 fMoleculeID = GetManager()->Insert(moleculeD 87 label, 88 this); 89 fElectronOccupancy = nullptr; 90 91 fDynCharge = charge; 92 93 fDynMass = fMoleculeDefinition->GetMass(); 94 95 fDynDiffusionCoefficient = fMoleculeDefiniti 96 fDynVanDerVaalsRadius = fMoleculeDefinition- 97 fDynDecayTime = fMoleculeDefinition->GetDeca 98 99 fName = fMoleculeDefinition->GetName(); 100 fName += "^"; 101 fName += G4UIcommand::ConvertToString(fDynCh 102 103 fFormatedName = fMoleculeDefinition->GetForm 104 fFormatedName += "^"; 105 fFormatedName += "{"; 106 fFormatedName += G4UIcommand::ConvertToStrin 107 fFormatedName += "}"; 108 109 fDiffParam = &G4MolecularConfiguration::Retu 110 fIsFinalized = false; 111 } 112 113 void G4MolecularConfiguration::MakeExceptionIf 114 { 115 if(fIsFinalized) 116 { 117 G4ExceptionDescription errMsg; 118 errMsg << "This molecular configuration " 119 << " is already finalized. Therefor 120 " properties cannot be changed."; 121 G4Exception("G4MolecularConfiguration::Mak 122 "CONF_FINALIZED",FatalExceptio 123 } 124 } 125 126 //____________________________________________ 127 128 G4MolecularConfiguration::G4MolecularConfigura 129 G4MolecularConfiguration::GetManager() 130 { 131 if (fgManager == nullptr) 132 { 133 G4AutoLock lock(&MolecularConfigurationMan 134 if (fgManager == nullptr) // double check 135 { 136 fgManager = new G4MolecularConfiguration 137 G4MolecularConfigurationManager(); 138 } 139 lock.unlock(); 140 } 141 142 return fgManager; 143 } 144 145 //____________________________________________ 146 147 G4MolecularConfiguration:: 148 G4MolecularConfigurationManager::~G4MolecularC 149 { 150 // G4cout << "Does G4AllocatorList exists= "; 151 // G4cout << (G4AllocatorList::GetAllocatorLi 152 // << G4endl; 153 154 G4MolecularConfigurationManager::MolElectron 155 G4MolecularConfigurationManager::ElectronOcc 156 iterator it2; 157 158 for (it1 = fElecOccTable.begin(); it1 != fEl 159 { 160 for (it2 = it1->second.begin(); it2 != it1 161 { 162 163 164 delete it2->second; 165 166 } 167 } 168 fElecOccTable.clear(); 169 fgManager = nullptr; 170 } 171 172 //____________________________________________ 173 // G4MolecularConfigurationManager 174 G4int G4MolecularConfiguration:: 175 G4MolecularConfigurationManager:: 176 Insert(const G4MoleculeDefinition* molDef, 177 const G4ElectronO 178 G4MolecularConfig 179 { 180 //G4AutoLock lock(&fMoleculeCreationMutex); 181 182 ElectronOccupancyTable& table2 = fElecOccTab 183 auto it = table2.find(eOcc); 184 185 if(it == table2.end()) 186 { 187 table2[eOcc] = molConf; 188 } 189 else 190 { 191 G4ExceptionDescription errMsg; 192 errMsg << "The same molecular configuratio 193 G4Exception("G4MolecularConfigurationManag 194 "SetMolecularConfiguration(con 195 "const G4ElectronOccupancy& eO 196 "G4MolecularConfiguration* mol 197 "", 198 FatalException, 199 errMsg 200 ); 201 } 202 203 fLastMoleculeID++; 204 205 fMolConfPerID.push_back(molConf); 206 207 //lock.unlock(); 208 return fLastMoleculeID; 209 } 210 211 //____________________________________________ 212 213 const G4ElectronOccupancy* 214 G4MolecularConfiguration::G4MolecularConfigura 215 FindCommonElectronOccupancy(const G4MoleculeDe 216 const G4ElectronOc 217 { 218 //G4AutoLock lock(&fMoleculeCreationMutex); 219 220 auto it1 = fElecOccTable.find(molDef); 221 222 if(it1 == fElecOccTable.end()) 223 { 224 // TODO = handle exception ? 225 return nullptr; 226 } 227 228 ElectronOccupancyTable& table2 = it1->second 229 auto it2 = table2.find(eOcc); 230 231 //lock.unlock(); 232 233 if (it2 == table2.end()) 234 { 235 // TODO = handle exception ? 236 return nullptr; 237 } 238 239 return &(it2->first); 240 } 241 242 //____________________________________________ 243 244 G4MolecularConfiguration* 245 G4MolecularConfiguration::G4MolecularConfigura 246 GetMolecularConfiguration(const G4MoleculeDefi 247 const G4ElectronOccu 248 { 249 auto it1 = fElecOccTable.find(molDef); 250 251 if(it1 == fElecOccTable.end()) return nullpt 252 253 ElectronOccupancyTable& table2 = it1->second 254 auto it = table2.find(eOcc); 255 256 if(it == table2.end()) 257 { 258 return nullptr; 259 } 260 261 return it->second; 262 } 263 264 //____________________________________________ 265 266 G4int G4MolecularConfiguration::G4MolecularCon 267 Insert(const G4MoleculeDefinition* molDef, 268 int charge, 269 G4MolecularConfiguration* molConf) 270 { 271 272 //G4AutoLock lock(&fMoleculeCreationMutex); 273 ChargeTable& table2 = fChargeTable[molDef]; 274 auto it = table2.find(charge); 275 276 if(it == table2.end()) 277 { 278 table2[charge] = molConf; 279 } 280 else 281 { 282 //lock.unlock(); 283 G4ExceptionDescription errMsg; 284 errMsg << "The same molecular configuratio 285 G4Exception("G4MolecularConfigurationManag 286 "SetMolecularConfiguration(con 287 "int charge," 288 "G4MolecularConfiguration* mol 289 "", FatalException, errMsg); 290 } 291 292 fLastMoleculeID++; 293 fMolConfPerID.push_back(molConf); 294 //lock.unlock(); 295 return fLastMoleculeID; 296 } 297 298 //____________________________________________ 299 300 G4MolecularConfiguration* 301 G4MolecularConfiguration::G4MolecularConfigura 302 GetMolecularConfiguration(const G4MoleculeDefi 303 int charge) 304 { 305 //G4AutoLock lock(&fMoleculeCreationMutex); 306 307 auto it1 = fChargeTable.find(molDef); 308 309 if(it1 == fChargeTable.end()) return nullptr 310 311 ChargeTable& table2 = it1->second; 312 auto it = table2.find(charge); 313 314 if(it == table2.end()) 315 { 316 return nullptr; 317 } 318 319 return it->second; 320 321 } 322 323 //____________________________________________ 324 // Static method in G4MolecularConfiguration 325 G4MolecularConfiguration* 326 G4MolecularConfiguration:: 327 GetOrCreateMolecularConfiguration(const G4Mole 328 { 329 if (molDef->GetGroundStateElectronOccupancy( 330 { 331 const G4ElectronOccupancy& elecOcc = 332 *molDef->GetGroundStateElectronOccupan 333 G4MolecularConfiguration* molConf = 334 GetManager()->GetMolecularConfiguratio 335 336 if (molConf != nullptr) 337 { 338 return molConf; 339 } 340 341 auto newConf = 342 new G4MolecularConfiguration(molDef, 343 elecOcc); 344 newConf->SetUserID(molDef->GetName()); 345 return newConf; 346 } 347 348 G4MolecularConfiguration* molConf = 349 GetManager()->GetMolecularConfiguration( 350 if(molConf != nullptr) 351 { 352 return molConf; 353 } 354 355 auto newConf = 356 new G4MolecularConfiguration(molDef, mol 357 newConf->SetUserID(molDef->GetName()); 358 return newConf; 359 } 360 361 //____________________________________________ 362 363 G4MolecularConfiguration* 364 G4MolecularConfiguration:: 365 GetOrCreateMolecularConfiguration(const G4Mole 366 const G4Elec 367 { 368 return GetManager()->GetOrCreateMolecularCon 369 370 // G4MolecularConfiguration* molConf = 371 // GetManager()->GetMolecularConfiguratio 372 // 373 // if (molConf) 374 // { 375 // return molConf; 376 // } 377 // else 378 // { 379 // G4MolecularConfiguration* newConf = 380 // new G4MolecularConfiguration(molDef, 381 // return newConf; 382 // } 383 } 384 385 //____________________________________________ 386 387 G4MolecularConfiguration* 388 G4MolecularConfiguration:: 389 GetOrCreateMolecularConfiguration(const G4Mole 390 int charge) 391 { 392 G4MolecularConfiguration* molConf = 393 GetManager()->GetMolecularConfiguration( 394 395 if(molConf != nullptr) 396 { 397 return molConf; 398 } 399 400 auto newConf = 401 new G4MolecularConfiguration(molDef, cha 402 return newConf; 403 } 404 405 //____________________________________________ 406 407 void G4MolecularConfiguration::DeleteManager() 408 { 409 G4AutoLock lock(&MolecularConfigurationManag 410 delete fgManager; 411 fgManager = nullptr; 412 lock.unlock(); 413 } 414 415 //____________________________________________ 416 // G4MolecularConfiguration 417 G4MolecularConfiguration:: 418 G4MolecularConfiguration(const G4MoleculeDefin 419 const G4ElectronOccup 420 const G4String& label 421 { 422 fMoleculeDefinition = moleculeDef; 423 424 fMoleculeID = GetManager()->Insert(moleculeD 425 elecOcc, 426 this); 427 fElectronOccupancy = GetManager()->FindCommo 428 429 430 /* 431 fgManager->fTable[fMoleculeDefinition][elec 432 std::map<G4ElectronOccupancy, G4MolecularCo 433 it = fgManager->fTable[moleculeDef].find(el 434 fElectronOccupancy = &(it->first); 435 */ 436 437 fDynCharge = fMoleculeDefinition->GetNbElect 438 - fElectronOccupancy->GetTotalOccupancy( 439 + moleculeDef->GetCharge(); 440 fDynMass = fMoleculeDefinition->GetMass(); 441 442 fDynDiffusionCoefficient = fMoleculeDefiniti 443 fDynVanDerVaalsRadius = fMoleculeDefinition- 444 fDynDecayTime = fMoleculeDefinition->GetDeca 445 446 fName = fMoleculeDefinition->GetName(); 447 fName += "^"; 448 fName += G4UIcommand::ConvertToString(fDynCh 449 450 fFormatedName = fMoleculeDefinition->GetForm 451 fFormatedName += "^"; 452 fFormatedName += "{"; 453 fFormatedName += G4UIcommand::ConvertToStrin 454 fFormatedName += "}"; 455 456 fLabel = nullptr; // let it here 457 458 if(!label.empty()) 459 { 460 SetLabel(label); 461 } 462 463 fDiffParam = &G4MolecularConfiguration::Retu 464 465 fIsFinalized = false; 466 } 467 468 //____________________________________________ 469 470 G4MolecularConfiguration:: 471 G4MolecularConfiguration(const G4MoleculeDefin 472 int charge) 473 { 474 fMoleculeDefinition = moleculeDef; 475 476 fMoleculeID = GetManager()->Insert(moleculeD 477 charge, 478 this); 479 fElectronOccupancy = nullptr; 480 481 fDynCharge = charge; 482 fDynMass = fMoleculeDefinition->GetMass(); 483 484 fDynDiffusionCoefficient = fMoleculeDefiniti 485 fDynVanDerVaalsRadius = fMoleculeDefinition- 486 fDynDecayTime = fMoleculeDefinition->GetDeca 487 488 fName = fMoleculeDefinition->GetName(); 489 fName += "^"; 490 fName += G4UIcommand::ConvertToString(fDynCh 491 492 fFormatedName = fMoleculeDefinition->GetForm 493 fFormatedName += "^"; 494 fFormatedName += "{"; 495 fFormatedName += G4UIcommand::ConvertToStrin 496 fFormatedName += "}"; 497 498 fLabel = nullptr; 499 500 fDiffParam = &G4MolecularConfiguration::Retu 501 502 fIsFinalized = false; 503 } 504 505 //____________________________________________ 506 507 G4MolecularConfiguration::~G4MolecularConfigur 508 { 509 if (fgManager != nullptr) fgManager->RemoveM 510 511 // if (G4AllocatorList::GetAllocatorListIfExi 512 // { 513 // if (fElectronOccupancy) 514 // { 515 // delete fElectronOccupancy; 516 // fElectronOccupancy = 0; 517 // } 518 // } 519 } 520 521 //____________________________________________ 522 523 G4MolecularConfiguration* 524 G4MolecularConfiguration:: 525 ChangeConfiguration(const G4ElectronOccupancy& 526 { 527 G4MolecularConfiguration* output = 528 GetManager()->GetMolecularConfiguration( 529 530 531 if (output == nullptr) 532 { 533 output = new G4MolecularConfiguration(fMol 534 newE 535 } 536 return output; 537 } 538 539 //____________________________________________ 540 541 G4MolecularConfiguration* 542 G4MolecularConfiguration::ChangeConfiguration( 543 { 544 G4MolecularConfiguration* output = 545 GetManager()->GetMolecularConfiguration( 546 547 if (output == nullptr) 548 { 549 output = new G4MolecularConfiguration(fMol 550 } 551 return output; 552 } 553 554 //____________________________________________ 555 556 G4MolecularConfiguration& 557 G4MolecularConfiguration::operator=(G4Molecula 558 { 559 // if (&right == this) return *this; 560 return *this; 561 } 562 563 //____________________________________________ 564 565 /** Method used in Geant4-DNA to excite water 566 */ 567 G4MolecularConfiguration* 568 G4MolecularConfiguration::ExciteMolecule(G4int 569 { 570 // MakeExceptionIfFinalized(); 571 CheckElectronOccupancy(__func__); 572 G4ElectronOccupancy newElectronOccupancy(*fE 573 574 newElectronOccupancy.RemoveElectron(ExcitedL 575 newElectronOccupancy.AddElectron(5, 1); 576 577 return ChangeConfiguration(newElectronOccupa 578 } 579 580 //____________________________________________ 581 582 /** Method used in Geant4-DNA to ionize water 583 */ 584 G4MolecularConfiguration* 585 G4MolecularConfiguration::IonizeMolecule(G4int 586 { 587 // MakeExceptionIfFinalized(); 588 CheckElectronOccupancy(__func__); 589 G4ElectronOccupancy newElectronOccupancy(*fE 590 591 if (newElectronOccupancy.GetOccupancy(Ionize 592 { 593 newElectronOccupancy.RemoveElectron(Ionize 594 } 595 else 596 { 597 G4String errMsg = "There is no electron on 598 + G4UIcommand::ConvertToString(Ionized 599 + " you want to free. The molecule's n 600 + GetName(); 601 G4Exception("G4MolecularConfiguration::Ion 602 "", 603 FatalErrorInArgument, 604 errMsg); 605 PrintState(); 606 } 607 608 // DEBUG 609 // PrintState(); 610 611 return ChangeConfiguration(newElectronOccupa 612 } 613 614 //____________________________________________ 615 616 G4MolecularConfiguration* G4MolecularConfigura 617 618 { 619 // MakeExceptionIfFinalized(); 620 CheckElectronOccupancy(__func__); 621 G4ElectronOccupancy newElectronOccupancy(*fE 622 newElectronOccupancy.AddElectron(orbit, numb 623 return ChangeConfiguration(newElectronOccupa 624 } 625 626 //____________________________________________ 627 628 G4MolecularConfiguration* 629 G4MolecularConfiguration::RemoveElectron(G4int 630 G4int 631 { 632 // MakeExceptionIfFinalized(); 633 CheckElectronOccupancy(__func__); 634 G4ElectronOccupancy newElectronOccupancy(*fE 635 636 if (newElectronOccupancy.GetOccupancy(orbit) 637 { 638 newElectronOccupancy.RemoveElectron(orbit, 639 } 640 else 641 { 642 G4String errMsg = "There is already no ele 643 + G4UIcommand::ConvertToString(orbit) 644 + " you want to free. The molecule's n 645 G4Exception("G4MolecularConfiguration::Rem 646 "", 647 JustWarning, 648 errMsg); 649 PrintState(); 650 } 651 652 return ChangeConfiguration(newElectronOccupa 653 } 654 655 //____________________________________________ 656 657 G4MolecularConfiguration* 658 G4MolecularConfiguration::MoveOneElectron(G4in 659 G4in 660 { 661 // MakeExceptionIfFinalized(); 662 CheckElectronOccupancy(__func__); 663 G4ElectronOccupancy newElectronOccupancy(*fE 664 665 if (newElectronOccupancy.GetOccupancy(orbitT 666 { 667 newElectronOccupancy.RemoveElectron(orbitT 668 newElectronOccupancy.AddElectron(orbitToFi 669 } 670 else 671 { 672 G4String errMsg = "There is no electron on 673 + G4UIcommand::ConvertToString(orbitTo 674 + " you want to free. The molecule's n 675 G4Exception("G4MolecularConfiguration::Mov 676 "", 677 FatalErrorInArgument, 678 errMsg); 679 PrintState(); 680 } 681 682 return ChangeConfiguration(newElectronOccupa 683 } 684 685 //____________________________________________ 686 687 const G4String& G4MolecularConfiguration::GetN 688 { 689 return fName; 690 } 691 692 //____________________________________________ 693 694 const G4String& G4MolecularConfiguration::GetF 695 { 696 return fFormatedName; 697 } 698 699 //____________________________________________ 700 701 G4int G4MolecularConfiguration::GetAtomsNumber 702 { 703 return fMoleculeDefinition->GetAtomsNumber() 704 } 705 706 //____________________________________________ 707 708 G4double G4MolecularConfiguration::GetNbElectr 709 { 710 CheckElectronOccupancy(__func__); 711 return fElectronOccupancy->GetTotalOccupancy 712 } 713 714 //____________________________________________ 715 716 void G4MolecularConfiguration::PrintState() co 717 { 718 G4cout << "-------------- Start Printing Sta 719 << " ---------------" << G4endl; 720 721 if (fElectronOccupancy != nullptr) 722 { 723 G4cout << "--------------Print electronic 724 << "---------------" << G4endl; 725 fElectronOccupancy->DumpInfo(); 726 if(fElectronOccupancy==fMoleculeDefinition 727 { 728 G4cout<<"At ground state"<<G4endl; 729 } 730 } 731 else 732 { 733 G4cout << "--- No electron occupancy set u 734 } 735 736 G4cout << "Charge :" 737 << fDynCharge 738 << G4endl; 739 740 if(fLabel != nullptr) 741 { 742 G4cout << "Label :" 743 << GetLabel() 744 << G4endl; 745 } 746 G4cout << "-------------- End Of State " << 747 << " -----------------------" << G4e 748 } 749 750 //____________________________________________ 751 752 // added - to be transformed in a "Decay metho 753 const vector<const G4MolecularDissociationChan 754 G4MolecularConfiguration::GetDissociationCha 755 { 756 // if (fElectronOccupancy == 0) return 0; 757 return fMoleculeDefinition->GetDecayChannels 758 } 759 760 //____________________________________________ 761 762 G4int G4MolecularConfiguration::GetFakeParticl 763 { 764 if(fMoleculeDefinition != nullptr) return fM 765 G4Exception("G4MolecularConfiguration::GetMo 766 "", 767 FatalErrorInArgument, 768 "You should first enter a m 769 770 return INT_MAX; 771 } 772 773 //____________________________________________ 774 775 const char* removePath(const char* path) 776 { 777 const char* pDelimeter = strrchr(path, '\\') 778 if (pDelimeter != nullptr) path = pDelimeter 779 780 pDelimeter = strrchr(path, '/'); 781 if (pDelimeter != nullptr) path = pDelimeter 782 783 return path; 784 } 785 786 //____________________________________________ 787 788 void G4MolecularConfiguration::CheckElectronOc 789 { 790 if (fElectronOccupancy == nullptr) 791 { 792 G4String functionName(function); 793 G4ExceptionDescription description; 794 description 795 << "No G4ElectronOccupancy was defined 796 << fMoleculeDefinition->GetName() 797 << ". The definition was probably defi 798 "rather than electron state."; 799 800 G4Exception(functionName, "", FatalErrorIn 801 } 802 } 803 804 //____________________________________________ 805 806 void G4MolecularConfiguration::G4MolecularConf 807 RecordNewlyLabeledConfiguration(G4MolecularCon 808 { 809 //G4AutoLock lock(&fMoleculeCreationMutex); 810 811 LabelTable& tmpMap = fLabelTable[molConf->fM 812 813 auto it = tmpMap.find(*molConf->fLabel); 814 815 if(it == tmpMap.end()) 816 { 817 tmpMap[*(molConf->fLabel)] = molConf; 818 } 819 else 820 { 821 G4ExceptionDescription errMsg; 822 errMsg << "The same molecular configuratio 823 G4Exception("G4MolecularConfigurationManag 824 "SetMolecularConfiguration(con 825 "const G4String& label," 826 "G4MolecularConfiguration* mol 827 "", FatalException, errMsg); 828 } 829 830 //lock.unlock(); 831 } 832 833 void G4MolecularConfiguration::G4MolecularConf 834 835 { 836 auto it = fUserIDTable.find(userID); 837 838 if(it == fUserIDTable.end()) 839 { 840 fUserIDTable[userID] = molecule; 841 } 842 else if(molecule != it->second) 843 { 844 // TODO improve exception 845 // exception 846 G4ExceptionDescription description; 847 description << "The user identifier " << u 848 << " was already given in anot 849 << G4endl; 850 G4Exception("G4MolecularConfiguration::G4Mol 851 "CONF_ALREADY_RECORDED", 852 FatalException, 853 description); 854 } 855 } 856 857 //____________________________________________ 858 859 void G4MolecularConfiguration::G4MolecularConf 860 RemoveMolecularConfigurationFromTable(G4Molecu 861 { 862 auto it1 = 863 fElecOccTable.find(configuration->GetDef 864 auto end = fElecOccTable.end(); 865 866 if (it1 == end) return; 867 868 auto it2 = 869 it1->second.find(*configuration->GetElec 870 871 if (it2 == it1->second.end()) return; 872 873 it2->second = 0; 874 // it1->second.erase(it2); 875 876 configuration->fElectronOccupancy = nullptr; 877 } 878 879 //____________________________________________ 880 881 G4MolecularConfiguration* 882 G4MolecularConfiguration::G4MolecularConfigura 883 GetMolecularConfiguration(const G4MoleculeDefi 884 const G4String& labe 885 { 886 //G4AutoLock lock(&fMoleculeCreationMutex); 887 888 auto it1 = fLabelTable.find(molDef); 889 890 if(it1 == fLabelTable.end()) return nullptr; 891 892 LabelTable& table2 = it1->second; 893 894 auto it2 = table2.find(label); 895 896 //lock.unlock(); 897 898 if(it2 == table2.end()) return nullptr; 899 return it2->second; 900 } 901 902 //____________________________________________ 903 904 G4MolecularConfiguration* 905 G4MolecularConfiguration::G4MolecularConfigura 906 GetMolecularConfiguration(int moleculeID) 907 { 908 if(moleculeID > (int) fMolConfPerID.size() | 909 moleculeID < 0) return nullptr; 910 911 return fMolConfPerID[moleculeID]; 912 } 913 914 //____________________________________________ 915 916 G4int 917 G4MolecularConfiguration::G4MolecularConfigura 918 Insert(const G4MoleculeDefinition* molDef, 919 const G4String& l 920 G4MolecularConfig 921 { 922 G4AutoLock lock(&fMoleculeCreationMutex); 923 LabelTable& tmpMap = fLabelTable[molDef]; 924 auto it = tmpMap.find(label); 925 926 if(it == tmpMap.end()) 927 { 928 fLastMoleculeID++; 929 tmpMap[label] = molConf; 930 lock.unlock(); 931 } 932 else 933 { 934 lock.unlock(); 935 G4ExceptionDescription errMsg; 936 errMsg << "The same molecular configuratio 937 G4Exception("G4MolecularConfigurationManag 938 "SetMolecularConfiguration(con 939 "const G4String& label," 940 "G4MolecularConfiguration* mol 941 "", FatalException, errMsg); 942 } 943 944 fMolConfPerID.push_back(molConf); 945 946 return fLastMoleculeID; 947 } 948 949 //____________________________________________ 950 951 G4MolecularConfiguration* 952 G4MolecularConfiguration::GetMolecularConfigur 953 954 { 955 return GetManager()->GetMolecularConfigurati 956 } 957 958 //____________________________________________ 959 960 G4MolecularConfiguration* 961 G4MolecularConfiguration::GetMolecularConfigur 962 { 963 return GetManager()->GetMolecularConfigurati 964 } 965 966 //____________________________________________ 967 968 G4MolecularConfiguration* 969 G4MolecularConfiguration::CreateMolecularConfi 970 971 972 973 974 { 975 wasAlreadyCreated = false; 976 G4MolecularConfiguration* molConf = 977 GetManager()->GetMolecularConfiguration( 978 979 if (molConf != nullptr) 980 { 981 if(molConf->fLabel == nullptr) 982 { 983 molConf->SetLabel(label); 984 G4ExceptionDescription wMsg ; 985 wMsg << "The molecular configuration for 986 << molDef->GetName() 987 << " with charge " << charge << " 988 "but with NO label"; 989 G4Exception("G4MolecularConfiguration::C 990 "DOUBLE_CREATION", 991 JustWarning, 992 wMsg); 993 } 994 else if(molConf->fLabel->empty() ) 995 { 996 molConf->SetLabel(label); 997 } 998 else if(*(molConf->fLabel) != label) 999 { 1000 G4ExceptionDescription errMsg ; 1001 errMsg << "The molecular configuration 1002 << molDef->GetName() 1003 << " with charge " << charge << 1004 "but with a different label 1005 << molConf->GetLabel(); 1006 G4Exception("G4MolecularConfiguration:: 1007 "DOUBLE_CREATION", 1008 FatalErrorInArgument, 1009 errMsg); 1010 // KILL APP 1011 } 1012 1013 if(molConf->fUserIdentifier.empty()) 1014 { 1015 molConf->fUserIdentifier = userIdentifi 1016 1017 G4ExceptionDescription wMsg ; 1018 wMsg << "The molecular configuration fo 1019 << molDef->GetName() 1020 << " with label " << label << " 1021 G4Exception("G4MolecularConfiguration:: 1022 "DOUBLE_CREATION", 1023 JustWarning, 1024 wMsg); 1025 } 1026 else if(molConf->fUserIdentifier != userI 1027 { 1028 G4ExceptionDescription errMsg ; 1029 errMsg << "The molecular configuration 1030 << molDef->GetName() 1031 << " with label " << label << " 1032 "BUT with a different user I 1033 << molConf->fUserIdentifier; 1034 G4Exception("G4MolecularConfiguration:: 1035 "DOUBLE_CREATION", 1036 FatalErrorInArgument, 1037 errMsg); 1038 // KILL APP 1039 } 1040 1041 wasAlreadyCreated = true; 1042 return molConf; 1043 } 1044 1045 auto newConf = 1046 new G4MolecularConfiguration(molDef, la 1047 newConf->fUserIdentifier = userIdentifier; 1048 1049 GetManager()->AddUserID(userIdentifier, new 1050 1051 // G4MoleculeTable::Instance()->RecordMole 1052 // 1053 return newConf; 1054 } 1055 1056 //___________________________________________ 1057 1058 G4MolecularConfiguration* 1059 G4MolecularConfiguration:: 1060 CreateMolecularConfiguration(const G4String& 1061 const G4Molecule 1062 bool& wasAlready 1063 { 1064 wasAlreadyCreated = false; 1065 G4MolecularConfiguration* preRegisteredMolC 1066 GetManager()->GetMolecularConfiguration 1067 1068 if(preRegisteredMolConf != nullptr) 1069 { 1070 if(preRegisteredMolConf->GetDefinition() 1071 { 1072 wasAlreadyCreated = true; 1073 return preRegisteredMolConf; 1074 } 1075 } 1076 1077 if(molDef->GetGroundStateElectronOccupancy( 1078 { 1079 const G4ElectronOccupancy& elecOcc = *mol 1080 ->GetGroundStateElectronOccupancy(); 1081 G4MolecularConfiguration* molConf = 1082 GetManager()->GetMolecularConfigurati 1083 1084 if(molConf != nullptr) 1085 { 1086 if(molConf->fUserIdentifier.empty()) 1087 { 1088 molConf->fUserIdentifier = userIdenti 1089 } 1090 else if(molConf->fUserIdentifier != use 1091 { 1092 G4ExceptionDescription errMsg; 1093 errMsg << "A molecular configuration 1094 << molDef->GetName() << " has 1095 "and recorded with a different 1096 << molConf->fUserIdentifier; 1097 G4Exception("G4MolecularConfiguration 1098 "DOUBLE_CREATION", 1099 FatalErrorInArgument, 1100 errMsg); 1101 } 1102 // TODO exception 1103 G4ExceptionDescription errMsg; 1104 errMsg << "A molecular configuration fo 1105 << molDef->GetName() << " has al 1106 G4Exception("G4MolecularConfiguration:: 1107 "DOUBLE_CREATION", 1108 JustWarning, 1109 errMsg); 1110 wasAlreadyCreated = true; 1111 return molConf; 1112 } 1113 1114 // G4cout << "Create molConf for " << mol 1115 auto newConf = new G4MolecularConfigurat 1116 1117 newConf->fUserIdentifier = userIdentifier 1118 1119 GetManager()->AddUserID(userIdentifier, n 1120 1121 // G4MoleculeTable::Instance()->RecordMo 1122 // 1123 return newConf; 1124 } 1125 1126 return CreateMolecularConfiguration(userIde 1127 molDef, 1128 molDef- 1129 molDef- 1130 wasAlre 1131 } 1132 1133 //___________________________________________ 1134 1135 G4MolecularConfiguration* 1136 G4MolecularConfiguration:: 1137 CreateMolecularConfiguration(const G4String& 1138 const G4Molecule 1139 const G4String& 1140 bool& wasAlready 1141 { 1142 assert(label != ""); 1143 wasAlreadyCreated = false; 1144 1145 G4MolecularConfiguration* molConf = 1146 GetManager()->GetMolecularConfiguration 1147 if(molConf != nullptr) 1148 { 1149 if((molConf->fLabel != nullptr) 1150 && *molConf->fLabel == label) 1151 { 1152 wasAlreadyCreated = true; 1153 return molConf; 1154 } 1155 if(molConf->fLabel == nullptr) 1156 { 1157 wasAlreadyCreated = true; 1158 molConf->SetLabel(label); 1159 return molConf; 1160 } 1161 if(molConf->fLabel->empty()) 1162 { 1163 wasAlreadyCreated = true; 1164 molConf->SetLabel(label); 1165 return molConf; 1166 } 1167 1168 molConf->PrintState(); 1169 G4ExceptionDescription errMsg ; 1170 errMsg << "A molecular configuration for 1171 << molDef->GetName() 1172 << " has already been created " 1173 "with user ID " 1174 << molConf->fUserIdentifier << " a 1175 << molConf->GetLabel(); 1176 G4Exception("G4MolecularConfiguration::Cr 1177 "DOUBLE_CREATION", 1178 FatalErrorInArgument, 1179 errMsg); 1180 // KILL APP 1181 } 1182 else 1183 { 1184 auto newConf = 1185 new G4MolecularConfiguration(molDef, 1186 label, 1187 molDef->Ge 1188 newConf->fUserIdentifier = userIdentifier 1189 1190 GetManager()->AddUserID(userIdentifier, n 1191 1192 // G4MoleculeTable::Instance()-> 1193 // RecordMolecularConfiguration(userId 1194 return newConf; 1195 } 1196 return molConf; 1197 } 1198 1199 //___________________________________________ 1200 1201 G4MolecularConfiguration* 1202 G4MolecularConfiguration:: 1203 CreateMolecularConfiguration(const G4String& 1204 const G4Molecule 1205 const G4String& 1206 const G4Electron 1207 bool& wasAlready 1208 { 1209 assert(label != ""); 1210 wasAlreadyCreated = false; 1211 1212 G4MolecularConfiguration* molConf = 1213 GetManager()->GetMolecularConfiguration 1214 1215 if(molConf != nullptr) 1216 { 1217 if(molConf->GetElectronOccupancy() != nul 1218 { 1219 if(*molConf->GetElectronOccupancy() == 1220 { 1221 if((molConf->fLabel != nullptr) && *m 1222 { 1223 wasAlreadyCreated = true; 1224 return molConf; 1225 } 1226 if(molConf->fLabel == nullptr) 1227 { 1228 wasAlreadyCreated = true; 1229 molConf->SetLabel(label); 1230 return molConf; 1231 } 1232 if(molConf->fLabel->empty()) 1233 { 1234 wasAlreadyCreated = true; 1235 molConf->SetLabel(label); 1236 return molConf; 1237 } 1238 } 1239 } 1240 1241 1242 molConf->PrintState(); 1243 G4ExceptionDescription errMsg ; 1244 errMsg << "A molecular configuration for 1245 << molDef->GetName() 1246 << " has already been created " 1247 "with user ID " 1248 << molConf->fUserIdentifier 1249 << " and possible different electr 1250 G4Exception("G4MolecularConfiguration::Cr 1251 "DOUBLE_CREATION", 1252 FatalErrorInArgument, 1253 errMsg); 1254 } 1255 else 1256 { 1257 auto newConf = 1258 new G4MolecularConfiguration(molDef, 1259 eOcc, 1260 label); 1261 newConf->fUserIdentifier = userIdentifier 1262 1263 GetManager()->AddUserID(userIdentifier, n 1264 1265 // G4MoleculeTable::Instance()-> 1266 // RecordMolecularConfiguration(userId 1267 return newConf; 1268 } 1269 return molConf; 1270 } 1271 1272 1273 //___________________________________________ 1274 1275 G4MolecularConfiguration* 1276 G4MolecularConfiguration::G4MolecularConfigur 1277 GetOrCreateMolecularConfiguration(const G4Mol 1278 const G4Ele 1279 { 1280 auto it1 = fElecOccTable.find(molDef); 1281 1282 if(it1 == fElecOccTable.end()) 1283 { 1284 return new G4MolecularConfiguration(molDe 1285 } 1286 1287 ElectronOccupancyTable& table2 = it1->secon 1288 auto it = table2.find(eOcc); 1289 1290 if(it == table2.end()) 1291 { 1292 auto molConf = 1293 new G4MolecularConfiguration(molDef, 1294 // molConf->Finalize(); 1295 return molConf; 1296 } 1297 1298 return it->second; 1299 } 1300 1301 //___________________________________________ 1302 1303 G4MolecularConfiguration* 1304 G4MolecularConfiguration::G4MolecularConfigur 1305 GetOrCreateMolecularConfiguration(const G4Mol 1306 int charge) 1307 { 1308 auto it1 = fChargeTable.find(molDef); 1309 1310 if(it1 == fChargeTable.end()) 1311 { 1312 G4AutoLock lock(&fMoleculeCreationMutex); 1313 1314 auto newConf = new G4MolecularConfigurat 1315 return newConf ; 1316 } 1317 1318 ChargeTable& table2 = it1->second; 1319 auto it = table2.find(charge); 1320 1321 if(it == table2.end()) 1322 { 1323 G4AutoLock lock(&fMoleculeCreationMutex); 1324 1325 auto newConf = 1326 new G4MolecularConfiguration(molDef, 1327 // newConf->Finalize(); 1328 return newConf ; 1329 } 1330 1331 return it->second; 1332 } 1333 1334 //___________________________________________ 1335 1336 void G4MolecularConfiguration::Serialize(std: 1337 { 1338 G4String moleculeName = fMoleculeDefinition 1339 WRITE(out, moleculeName); 1340 1341 // if(fLabel) 1342 // out << fLabel; 1343 // else 1344 // out << ""; 1345 WRITE(out,fDynDiffusionCoefficient); 1346 WRITE(out,fDynVanDerVaalsRadius); 1347 WRITE(out,fDynDecayTime); 1348 WRITE(out,fDynMass); 1349 WRITE(out,fDynCharge); 1350 WRITE(out,fMoleculeID); 1351 WRITE(out,fFormatedName); 1352 WRITE(out,fName); 1353 WRITE(out,fIsFinalized); 1354 } 1355 1356 //___________________________________________ 1357 1358 void G4MolecularConfiguration::Unserialize(st 1359 { 1360 G4String moleculeName; 1361 READ(in, moleculeName); 1362 fMoleculeDefinition = 1363 G4MoleculeTable::Instance()->GetMolecul 1364 1365 // G4String label; 1366 // 1367 // in.read((char*)(&label), sizeof(label)); 1368 // 1369 // if(label) 1370 // fLabel = new G4String(label); 1371 // else 1372 // fLabel = 0; 1373 READ(in,fDynDiffusionCoefficient); 1374 READ(in,fDynVanDerVaalsRadius); 1375 READ(in,fDynDecayTime); 1376 READ(in,fDynMass); 1377 READ(in,fDynCharge); 1378 READ(in,fMoleculeID); 1379 READ(in,fFormatedName); 1380 READ(in,fName); 1381 READ(in,fIsFinalized); 1382 } 1383 1384 //___________________________________________ 1385 1386 G4MolecularConfiguration* G4MolecularConfigur 1387 { 1388 return new G4MolecularConfiguration(in); 1389 } 1390 1391 //___________________________________________ 1392 1393 G4MolecularConfiguration::G4MolecularConfigur 1394 { 1395 fLabel = nullptr; // TODO: for now not seri 1396 Unserialize(in); 1397 fMoleculeDefinition = nullptr; 1398 fElectronOccupancy = nullptr; 1399 if(fElectronOccupancy != nullptr) 1400 { 1401 GetManager()->Insert(fMoleculeDefinition, 1402 fElectronOccupancy = 1403 GetManager()->FindCommonElectronOccup 1404 1405 1406 if(fLabel != nullptr) 1407 { 1408 GetManager()->RecordNewlyLabeledConfigu 1409 } 1410 } 1411 else if(fLabel != nullptr) 1412 { 1413 fMoleculeID = GetManager()->Insert(fMolec 1414 } 1415 else if(fDynCharge != 0) 1416 { 1417 fMoleculeID = GetManager()->Insert(fMolec 1418 } 1419 } 1420 1421 //___________________________________________ 1422 1423 void G4MolecularConfiguration::SetUserID(cons 1424 { 1425 fUserIdentifier = userID; 1426 GetManager()->AddUserID(userID, this); 1427 // G4MoleculeTable::Instance()->RecordMolecu 1428 } 1429 1430 //___________________________________________ 1431 1432 double G4MolecularConfiguration::DiffCoeffWat 1433 { 1434 return pow(10, 4.311 1435 - 2.722e3/temperature_K 1436 + 8.565e5/(temperature_K *temper 1437 - 1.181e8/(temperature_K*tempera 1438 } 1439 1440 //___________________________________________ 1441 1442 void 1443 G4MolecularConfiguration:: 1444 ScaleAllDiffusionCoefficientsOnWater(double t 1445 { 1446 double D_water_0 = DiffCoeffWater(fgTempera 1447 double D_water_f = DiffCoeffWater(temperatu 1448 1449 G4cout << "Scaling factor = " << D_water_f/ 1450 1451 G4ConfigurationIterator it = 1452 G4MoleculeTable::Instance()->GetConfigu 1453 1454 while(it()) 1455 { 1456 G4MolecularConfiguration* conf = it.value 1457 double D_0 = conf->GetDiffusionCoefficien 1458 double D_f = D_water_f * D_0 /D_water_0; 1459 conf->SetDiffusionCoefficient(D_f); 1460 }; 1461 } 1462 1463 //___________________________________________ 1464 1465 void G4MolecularConfiguration::CreateDefaultD 1466 { 1467 if(!static_cast<bool>(fDiffParam)) 1468 { 1469 fDiffParam = &G4MolecularConfiguration::R 1470 } 1471 } 1472 1473 //___________________________________________ 1474 1475 void G4MolecularConfiguration::SetGlobalTempe 1476 { 1477 ScaleAllDiffusionCoefficientsOnWater(temper 1478 fgTemperature = temperature; 1479 } 1480 1481 //___________________________________________ 1482 1483 G4double G4MolecularConfiguration::GetGlobalT 1484 { 1485 return fgTemperature; 1486 } 1487 1488 //___________________________________________ 1489 1490 G4MolecularConfiguration* 1491 G4MolecularConfiguration:: 1492 G4MolecularConfigurationManager::GetMolecular 1493 { 1494 for(auto it : fMolConfPerID) 1495 { 1496 if(it->GetUserID() == userID) return it; 1497 } 1498 return nullptr; 1499 } 1500 1501 //___________________________________________ 1502 1503 G4MolecularConfiguration* 1504 G4MolecularConfiguration::GetMolecularConfigu 1505 { 1506 return GetManager()->GetMolecularConfigurat 1507 } 1508 1509 //___________________________________________ 1510 1511 void G4MolecularConfiguration::FinalizeAll() 1512 { 1513 const std::vector<G4MolecularConfiguration* 1514 GetManager()->GetAllSpecies(); 1515 1516 for(auto specie : species) 1517 { 1518 specie->Finalize(); 1519 } 1520 1521 } 1522 1523 void G4MolecularConfiguration::PrintAll() //h 1524 { 1525 const std::vector<G4MolecularConfiguration* 1526 GetManager()->GetAllSpecies(); 1527 G4cout<<G4endl; 1528 G4cout<<"Molecular Config"<<std::setw(25)<< 1529 G4cout<<"__________________________________ 1530 "________________________________ 1531 for(auto specie : species) 1532 { 1533 G4cout<<specie->GetName() 1534 <<std::setw(G4int(30 - specie->Get 1535 <<right<<specie->GetDiffusionCoeff 1536 <<specie->GetVanDerVaalsRadius()/C 1537 G4cout<<"________________________________ 1538 "______________________________ 1539 } 1540 1541 } 1542