Geant4 Cross Reference |
1 // 1 // 2 // ******************************************* 2 // ******************************************************************** 3 // * License and Disclaimer 3 // * License and Disclaimer * 4 // * 4 // * * 5 // * The Geant4 software is copyright of th 5 // * The Geant4 software is copyright of the Copyright Holders of * 6 // * the Geant4 Collaboration. It is provided 6 // * the Geant4 Collaboration. It is provided under the terms and * 7 // * conditions of the Geant4 Software License 7 // * conditions of the Geant4 Software License, included in the file * 8 // * LICENSE and available at http://cern.ch/ 8 // * LICENSE and available at http://cern.ch/geant4/license . These * 9 // * include a list of copyright holders. 9 // * include a list of copyright holders. * 10 // * 10 // * * 11 // * Neither the authors of this software syst 11 // * Neither the authors of this software system, nor their employing * 12 // * institutes,nor the agencies providing fin 12 // * institutes,nor the agencies providing financial support for this * 13 // * work make any representation or warran 13 // * work make any representation or warranty, express or implied, * 14 // * regarding this software system or assum 14 // * regarding this software system or assume any liability for its * 15 // * use. Please see the license in the file 15 // * use. Please see the license in the file LICENSE and URL above * 16 // * for the full disclaimer and the limitatio 16 // * for the full disclaimer and the limitation of liability. * 17 // * 17 // * * 18 // * This code implementation is the result 18 // * This code implementation is the result of the scientific and * 19 // * technical work of the GEANT4 collaboratio 19 // * technical work of the GEANT4 collaboration. * 20 // * By using, copying, modifying or distri 20 // * By using, copying, modifying or distributing the software (or * 21 // * any work based on the software) you ag 21 // * any work based on the software) you agree to acknowledge its * 22 // * use in resulting scientific publicati 22 // * use in resulting scientific publications, and indicate your * 23 // * acceptance of all terms of the Geant4 Sof 23 // * acceptance of all terms of the Geant4 Software license. * 24 // ******************************************* 24 // ******************************************************************** 25 // 25 // >> 26 // $Id$ 26 // 27 // 27 // Author: Ivana Hrivnacova, 04/10/2016 (ivan 28 // Author: Ivana Hrivnacova, 04/10/2016 (ivana@ipno.in2p3.fr) 28 29 29 #include "G4NtupleBookingManager.hh" << 30 #include "G4RootPNtupleManager.hh" 30 #include "G4RootPNtupleManager.hh" >> 31 #include "G4RootMainNtupleManager.hh" 31 #include "G4AnalysisUtilities.hh" 32 #include "G4AnalysisUtilities.hh" 32 33 33 #include "tools/wroot/file" 34 #include "tools/wroot/file" 34 #include "tools/wroot/ntuple" 35 #include "tools/wroot/ntuple" 35 36 36 using namespace G4Analysis; << 37 using std::to_string; << 38 << 39 // mutex in a file scope 37 // mutex in a file scope 40 namespace { 38 namespace { 41 << 39 //Mutex to lock master manager when adding ntuple row 42 //Mutex to lock master manager when adding ntu << 40 G4Mutex addRowMutex = G4MUTEX_INITIALIZER; 43 G4Mutex pntupleMutex = G4MUTEX_INITIALIZER; << 41 G4Mutex endFillMutex = G4MUTEX_INITIALIZER; 44 //Mutex to lock master manager when createing << 45 G4Mutex createMainMutex = G4MUTEX_INITIALIZER; << 46 << 47 //____________________________________________ << 48 void NotExistWarning(const G4String& what, G4i << 49 std::string_view classNam << 50 std::string_view function << 51 { << 52 Warn(what + " id= " + to_string(id) + " does << 53 className, functionName); << 54 << 55 } << 56 << 57 } 42 } 58 43 59 //____________________________________________ 44 //_____________________________________________________________________________ 60 G4RootPNtupleManager::G4RootPNtupleManager(con << 45 G4RootPNtupleManager::G4RootPNtupleManager(G4RootMainNtupleManager* main, 61 std::shared_ptr<G4Ntup << 46 const G4AnalysisManagerState& state) 62 std::shared_ptr<G4Root << 63 G4bool rowWise, G4bool << 64 : G4BaseNtupleManager(state), 47 : G4BaseNtupleManager(state), 65 fBookingManager(std::move(bookingManger)), << 48 fCreateMode(G4PNtupleCreateMode::kUndefined), 66 fMainNtupleManager(std::move(main)), << 49 fMainNtupleManager(main), 67 fRowWise(rowWise), << 50 fNtupleVector() 68 fRowMode(rowMode) << 69 {} 51 {} 70 52 71 //____________________________________________ 53 //_____________________________________________________________________________ 72 G4RootPNtupleManager::~G4RootPNtupleManager() 54 G4RootPNtupleManager::~G4RootPNtupleManager() 73 { 55 { 74 for ( auto ntupleDescription : fNtupleDescri 56 for ( auto ntupleDescription : fNtupleDescriptionVector ) { 75 delete ntupleDescription; 57 delete ntupleDescription; 76 } << 58 } 77 } 59 } 78 60 79 // 61 // 80 // private functions 62 // private functions 81 // 63 // 82 64 83 //____________________________________________ 65 //_____________________________________________________________________________ 84 G4RootPNtupleDescription* << 66 G4RootPNtupleDescription* 85 G4RootPNtupleManager::GetNtupleDescriptionInFu 67 G4RootPNtupleManager::GetNtupleDescriptionInFunction( 86 G4int id, std::string_view functionName, G4b << 68 G4int id, G4String functionName, G4bool warn) const 87 { << 69 { 88 auto index = id - fFirstId; 70 auto index = id - fFirstId; 89 if ( index < 0 || index >= G4int(fNtupleDesc 71 if ( index < 0 || index >= G4int(fNtupleDescriptionVector.size()) ) { 90 if ( warn) { 72 if ( warn) { 91 NotExistWarning("ntuple description", id << 73 G4String inFunction = "G4RootPNtupleManager::"; >> 74 inFunction += functionName; >> 75 G4ExceptionDescription description; >> 76 description << " " << "ntuple " << id << " does not exist."; >> 77 G4Exception(inFunction, "Analysis_W011", JustWarning, description); 92 } 78 } 93 return nullptr; << 79 return nullptr; 94 } 80 } 95 << 81 96 return fNtupleDescriptionVector[index]; 82 return fNtupleDescriptionVector[index]; 97 } 83 } 98 84 99 //____________________________________________ 85 //_____________________________________________________________________________ 100 tools::wroot::base_pntuple* << 86 tools::wroot::base_pntuple* 101 G4RootPNtupleManager::GetNtupleInFunction( 87 G4RootPNtupleManager::GetNtupleInFunction( 102 G4int id, std::string_view functionName, G4b << 88 G4int id, G4String functionName, G4bool warn) const 103 { << 89 { 104 auto ntupleDescription = GetNtupleDescriptio 90 auto ntupleDescription = GetNtupleDescriptionInFunction(id, functionName); 105 if (ntupleDescription == nullptr) return nul << 91 if ( ! ntupleDescription ) return nullptr; 106 92 107 if (ntupleDescription->GetBasePNtuple() == n << 93 if ( ! ntupleDescription->fBasePNtuple ) { 108 if ( warn ) { 94 if ( warn ) { 109 NotExistWarning("ntuple", id, fkClass, f << 95 G4String inFunction = "G4RootPNtupleManager::"; >> 96 inFunction += functionName; >> 97 G4ExceptionDescription description; >> 98 description << " " << "ntupleId " << id << " does not exist."; >> 99 G4Exception(inFunction, "Analysis_W011", JustWarning, description); 110 } 100 } 111 return nullptr; 101 return nullptr; 112 } << 102 } 113 return ntupleDescription->GetBasePNtuple(); << 103 return ntupleDescription->fBasePNtuple; 114 } 104 } 115 105 116 //____________________________________________ 106 //_____________________________________________________________________________ 117 tools::wroot::ntuple* 107 tools::wroot::ntuple* 118 G4RootPNtupleManager::GetMainNtupleInFunction( 108 G4RootPNtupleManager::GetMainNtupleInFunction( 119 G4int id, std::string_view functionName, G4b << 109 G4int id, G4String functionName, G4bool warn) const 120 { << 110 { 121 auto& mainNtupleVector = fMainNtupleManager- << 111 auto& mainNtupleVector 122 << 112 = fMainNtupleManager->GetNtupleVector(); >> 113 123 auto index = id - fFirstId; 114 auto index = id - fFirstId; 124 if ( index < 0 || index >= G4int(mainNtupleV 115 if ( index < 0 || index >= G4int(mainNtupleVector.size()) ) { 125 if ( warn) { 116 if ( warn) { 126 NotExistWarning("main ntuple", id, fkCla << 117 G4String inFunction = "G4RootPNtupleManager::"; >> 118 inFunction += functionName; >> 119 G4ExceptionDescription description; >> 120 description << " " << "main ntuple " << id << " does not exist."; >> 121 G4Exception(inFunction, "Analysis_W011", JustWarning, description); 127 } 122 } 128 return nullptr; << 123 return nullptr; 129 } 124 } 130 << 125 131 return mainNtupleVector[index]; 126 return mainNtupleVector[index]; 132 } 127 } 133 128 >> 129 134 // 130 // 135 // protected functions 131 // protected functions 136 // 132 // 137 133 138 //____________________________________________ 134 //_____________________________________________________________________________ 139 void G4RootPNtupleManager::CreateNtupleFromMai << 135 void G4RootPNtupleManager::CreateNtuple(G4RootPNtupleDescription* ntupleDescription, 140 G4RootPNtupleDesc << 136 tools::wroot::ntuple* mainNtuple) 141 tools::wroot::ntu << 137 { 142 { << 138 #ifdef G4VERBOSE 143 // Do not create pntuple if ntuple was delet << 139 if ( fState.GetVerboseL4() ) 144 if (mainNtuple == nullptr) { << 140 fState.GetVerboseL4() 145 ntupleDescription->SetNtuple(nullptr); << 141 ->Message("create from main", "pntuple", mainNtuple->name()); 146 ntupleDescription->SetBasePNtuple(nullptr) << 142 #endif 147 return; << 143 148 } << 144 auto rfile = fMainNtupleManager->GetNtupleFile(); 149 << 145 // auto directory = fMainNtupleManager->GetNtupleDirectory(); 150 Message(kVL4, "create from main", "pntuple", << 146 151 << 147 // Get parameters from main ntuple 152 auto file = fMainNtupleManager->GetNtupleFil << 148 auto mainBranch = mainNtuple->get_row_wise_branch(); 153 if ( ! file ) { << 149 auto rowWise = mainBranch ? true : false; 154 Warn("Cannot create pntuple. Main ntuple f << 155 fkClass, "CreateNtupleFromMain"); << 156 return; << 157 } << 158 << 159 ntupleDescription->GetDescription().SetFile( << 160 150 161 // Get parameters from ntupleDescription << 151 ntupleDescription->fFile = rfile.get(); 162 mainNtuple->get_branches(ntupleDescription-> << 152 mainNtuple->get_branches(ntupleDescription->fMainBranches); 163 153 164 auto rfile = std::get<0>(*file); << 165 G4bool verbose = true; 154 G4bool verbose = true; 166 if ( fRowWise ) { << 155 if ( rowWise ) { 167 auto mainBranch = mainNtuple->get_row_wise << 156 tools::wroot::mt_ntuple_row_wise* mtNtuple 168 auto mtNtuple << 169 = new tools::wroot::mt_ntuple_row_wise( 157 = new tools::wroot::mt_ntuple_row_wise( 170 G4cout, rfile->byte_swap(), rfil 158 G4cout, rfile->byte_swap(), rfile->compression(), 171 mainNtuple->dir().seek_directory 159 mainNtuple->dir().seek_directory(), 172 *mainBranch, mainBranch->basket_ << 160 *mainBranch, mainBranch->basket_size(), 173 ntupleDescription->GetDescriptio << 161 ntupleDescription->fNtupleBooking, verbose); 174 162 175 ntupleDescription->SetNtuple( << 163 ntupleDescription->fNtuple 176 static_cast<tools::wroot::imt_ntuple*>(m << 164 = static_cast<tools::wroot::imt_ntuple*>(mtNtuple); 177 ntupleDescription->SetBasePNtuple( << 165 ntupleDescription->fBasePNtuple 178 static_cast<tools::wroot::base_pntuple*> << 166 = static_cast<tools::wroot::base_pntuple*>(mtNtuple); 179 } << 167 } 180 else { 168 else { 181 std::vector<tools::uint32> basketSizes; 169 std::vector<tools::uint32> basketSizes; 182 tools_vforcit(tools::wroot::branch*, ntupl << 170 tools_vforcit(tools::wroot::branch*, ntupleDescription->fMainBranches, it) { 183 basketSizes.push_back((*it)->basket_size 171 basketSizes.push_back((*it)->basket_size()); 184 } 172 } 185 auto basketEntries = fMainNtupleManager->G << 173 186 << 174 tools::wroot::mt_ntuple_column_wise* mtNtuple = 187 auto mtNtuple = << 188 new tools::wroot::mt_ntuple_column_wise( 175 new tools::wroot::mt_ntuple_column_wise( 189 G4cout, rfile->byte_swap(), rfile- 176 G4cout, rfile->byte_swap(), rfile->compression(), 190 mainNtuple->dir().seek_directory() 177 mainNtuple->dir().seek_directory(), 191 ntupleDescription->GetMainBranches << 178 ntupleDescription->fMainBranches, basketSizes, 192 ntupleDescription->GetDescription( << 179 ntupleDescription->fNtupleBooking, verbose); 193 fRowMode, basketEntries, verbose); << 180 194 << 181 ntupleDescription->fNtuple 195 ntupleDescription->SetNtuple( << 182 = static_cast<tools::wroot::imt_ntuple*>(mtNtuple); 196 static_cast<tools::wroot::imt_ntuple*>(m << 183 ntupleDescription->fBasePNtuple 197 ntupleDescription->SetBasePNtuple( << 184 = static_cast<tools::wroot::base_pntuple*>(mtNtuple); 198 static_cast<tools::wroot::base_pntuple*> << 199 } 185 } 200 186 201 ntupleDescription->GetDescription().SetIsNtu << 187 ntupleDescription->fIsNtupleOwner = true; 202 // // pntuple object is not deleted a 188 // // pntuple object is not deleted automatically 203 fNtupleVector.push_back(ntupleDescription->G << 189 fNtupleVector.push_back(ntupleDescription->fNtuple); >> 190 204 191 205 Message(kVL3, "create from main", "pntuple", << 192 #ifdef G4VERBOSE >> 193 if ( fState.GetVerboseL3() ) >> 194 fState.GetVerboseL3() >> 195 ->Message("create from main", "pntuple", mainNtuple->name()); >> 196 #endif 206 } 197 } 207 198 208 //____________________________________________ 199 //_____________________________________________________________________________ 209 void G4RootPNtupleManager::CreateNtupleDescrip << 200 void G4RootPNtupleManager::CreateNtuplesFromMain() 210 { 201 { 211 // Create ntuple descriptions from booking. << 202 // Create ntuple from booking (if not yet done) and main ntuple 212 // This function is called from the first Fill << 203 // This function is called from G4AnalysisManager::OpenFile. 213 << 214 // Create pntuple descriptions from ntuple b << 215 auto g4NtupleBookings = fBookingManager->Get << 216 204 217 for ( auto g4NtupleBooking : g4NtupleBooking << 205 if ( fCreateMode == G4PNtupleCreateMode::kUndefined ) { 218 auto ntupleDescription = new G4RootPNtuple << 206 if ( fNtupleDescriptionVector.size() ) { 219 // Save g4booking, activation in pntuple b << 207 fCreateMode = G4PNtupleCreateMode::kSlaveBeforeOpen; 220 fNtupleDescriptionVector.push_back(ntupleD << 208 // G4cout << "Create mode: kSlaveBeforeOpen" << G4endl; >> 209 } else { >> 210 fCreateMode = G4PNtupleCreateMode::kSlaveAfterOpen; >> 211 // G4cout << "Create mode: kSlaveAfterOpen" << G4endl; >> 212 } 221 } 213 } 222 } << 223 214 224 //____________________________________________ << 215 if ( fCreateMode == G4PNtupleCreateMode::kSlaveAfterOpen ) { 225 void G4RootPNtupleManager::CreateNtuplesFromMa << 216 // ntuples are not yet booked 226 { << 217 // G4cout << "Ntuples are not yet booked ?" << G4endl; 227 // Create slave ntuples from main ntuple. << 218 return; 228 // This function is called from the first Fill << 219 } 229 220 230 auto& mainNtupleVector = fMainNtupleManager- << 221 auto& mainNtupleVector >> 222 = fMainNtupleManager->GetNtupleVector(); 231 223 232 G4int lcounter = 0; 224 G4int lcounter = 0; 233 for ( auto mainNtuple : mainNtupleVector ) { 225 for ( auto mainNtuple : mainNtupleVector ) { 234 auto& ntupleDescription = fNtupleDescripti << 226 235 CreateNtupleFromMain(ntupleDescription, ma << 227 auto& ntupleDescription >> 228 = fNtupleDescriptionVector[lcounter++]; >> 229 CreateNtuple(ntupleDescription, mainNtuple); 236 } 230 } 237 } 231 } 238 232 239 //____________________________________________ 233 //_____________________________________________________________________________ 240 void G4RootPNtupleManager::CreateNtuplesIfNeed << 234 G4int G4RootPNtupleManager::CreateNtuple( >> 235 const G4String& name, const G4String& title) 241 { 236 { 242 // The ntuples on workers are created at first << 237 // Create pntuple description with ntuple_booking 243 // (if only columns of vector type) call. << 244 // When writing multiple times in teh same fil << 245 // to be recreated as well. << 246 << 247 // G4cout << "G4RootPNtupleManager::CreateNt << 248 // << " fCreateNtuple: " << fCreateNtuples << 249 // << " fNewCycle: " << fNewCycle << 250 // << " fMainNtupleManager->GetNewCycle(): << 251 // << " fNtupleDescriptionVector.size(): " << 252 // << " fNtupleVector.size(): " << fNtuple << 253 // << G4endl; << 254 << 255 if (fCreateNtuples) { << 256 // create ntuple descriptions << 257 CreateNtupleDescriptionsFromBooking(); << 258 << 259 // create main ntuples if needed << 260 G4AutoLock lock(&createMainMutex); << 261 if (fMainNtupleManager->GetNewCycle()) { << 262 fMainNtupleManager->CreateNtuplesFromBoo << 263 } << 264 lock.unlock(); << 265 238 266 // create slave ntuples << 239 #ifdef G4VERBOSE 267 CreateNtuplesFromMain(); << 240 if ( fState.GetVerboseL4() ) 268 fCreateNtuples = false; << 241 fState.GetVerboseL4()->Message("create", "pntuple booking", name); 269 } << 242 #endif 270 243 271 if (fNewCycle) { << 244 // Set create mode if not yet defined 272 // create main ntuples if needed << 245 if ( fCreateMode == G4PNtupleCreateMode::kUndefined ) { 273 G4AutoLock lock(&createMainMutex); << 246 if ( fMainNtupleManager->GetNtupleFile() ) { 274 if (fMainNtupleManager->GetNewCycle()) { << 247 fCreateMode = G4PNtupleCreateMode::kSlaveAfterOpen; 275 fMainNtupleManager->CreateNtuplesFromBoo << 248 } else { >> 249 fCreateMode = G4PNtupleCreateMode::kSlaveBeforeOpen; 276 } 250 } 277 lock.unlock(); << 278 << 279 // create slave ntuples << 280 CreateNtuplesFromMain(); << 281 fNewCycle = false; << 282 } 251 } 283 } << 252 >> 253 // Create ntuple description >> 254 auto index = fNtupleDescriptionVector.size(); >> 255 auto ntupleDescription = new G4RootPNtupleDescription(); >> 256 fNtupleDescriptionVector.push_back(ntupleDescription); >> 257 >> 258 // Save name & title in ntuple booking >> 259 ntupleDescription->fNtupleBooking.set_name(name); >> 260 ntupleDescription->fNtupleBooking.set_title(title); >> 261 >> 262 fLockFirstId = true; >> 263 >> 264 #ifdef G4VERBOSE >> 265 if ( fState.GetVerboseL2() ) { >> 266 G4ExceptionDescription description; >> 267 description << name << " ntupleId " << index + fFirstId; >> 268 fState.GetVerboseL2()->Message("create", "pntuple booking", description); >> 269 } >> 270 #endif >> 271 >> 272 return index + fFirstId; >> 273 } >> 274 >> 275 //_____________________________________________________________________________ >> 276 G4int G4RootPNtupleManager::CreateNtupleIColumn( >> 277 G4int ntupleId, const G4String& name, std::vector<int>* vector) >> 278 { >> 279 return CreateNtupleTColumn<int>(ntupleId, name, vector); >> 280 } >> 281 >> 282 //_____________________________________________________________________________ >> 283 G4int G4RootPNtupleManager::CreateNtupleFColumn( >> 284 G4int ntupleId, const G4String& name, std::vector<float>* vector) >> 285 { >> 286 return CreateNtupleTColumn<float>(ntupleId, name, vector); >> 287 } >> 288 >> 289 >> 290 //_____________________________________________________________________________ >> 291 G4int G4RootPNtupleManager::CreateNtupleDColumn( >> 292 G4int ntupleId, const G4String& name, std::vector<double>* vector) >> 293 { >> 294 return CreateNtupleTColumn<double>(ntupleId, name, vector); >> 295 } 284 296 285 //____________________________________________ 297 //_____________________________________________________________________________ 286 G4int G4RootPNtupleManager::CreateNtuple(G4Ntu << 298 G4int G4RootPNtupleManager::CreateNtupleSColumn( >> 299 G4int ntupleId, const G4String& name) 287 { 300 { 288 // Create pntuple from g4 ntuple booking. << 301 return CreateNtupleTColumn<std::string>(ntupleId, name, nullptr); 289 // Nothing to be done here. << 302 } >> 303 >> 304 //_____________________________________________________________________________ >> 305 void G4RootPNtupleManager::FinishNtuple(G4int ntupleId) >> 306 { >> 307 // create ntuple if file was open 290 308 291 return G4Analysis::kInvalidId; << 309 // if ( fMainNtupleManager->GetNtupleFile() ) { >> 310 if ( fCreateMode == G4PNtupleCreateMode::kSlaveAfterOpen ) { >> 311 auto ntupleDescription >> 312 = GetNtupleDescriptionInFunction(ntupleId, "FinishNtuple"); >> 313 if ( ! ntupleDescription ) return; >> 314 >> 315 auto mainNtuple = GetMainNtupleInFunction(ntupleId, "FinishNtuple"); >> 316 if ( ! mainNtuple ) return; >> 317 >> 318 CreateNtuple(ntupleDescription, mainNtuple); >> 319 } 292 } 320 } 293 321 294 //____________________________________________ 322 //_____________________________________________________________________________ 295 G4bool G4RootPNtupleManager::FillNtupleIColumn 323 G4bool G4RootPNtupleManager::FillNtupleIColumn( 296 G4int ntupleId, G4int columnId, G4int value) 324 G4int ntupleId, G4int columnId, G4int value) 297 { 325 { 298 return FillNtupleTColumn<int>(ntupleId, colu 326 return FillNtupleTColumn<int>(ntupleId, columnId, value); 299 } << 327 } 300 328 301 //____________________________________________ 329 //_____________________________________________________________________________ 302 G4bool G4RootPNtupleManager::FillNtupleFColumn 330 G4bool G4RootPNtupleManager::FillNtupleFColumn( 303 G4int ntupleId, G4int columnId, G4float valu 331 G4int ntupleId, G4int columnId, G4float value) 304 { 332 { 305 return FillNtupleTColumn<float>(ntupleId, co 333 return FillNtupleTColumn<float>(ntupleId, columnId, value); 306 } << 334 } 307 335 308 //____________________________________________ 336 //_____________________________________________________________________________ 309 G4bool G4RootPNtupleManager::FillNtupleDColumn 337 G4bool G4RootPNtupleManager::FillNtupleDColumn( 310 G4int ntupleId, G4int columnId, G4double val 338 G4int ntupleId, G4int columnId, G4double value) 311 { 339 { 312 return FillNtupleTColumn<double>(ntupleId, c 340 return FillNtupleTColumn<double>(ntupleId, columnId, value); 313 } << 341 } 314 342 315 //____________________________________________ 343 //_____________________________________________________________________________ 316 G4bool G4RootPNtupleManager::FillNtupleSColumn 344 G4bool G4RootPNtupleManager::FillNtupleSColumn( 317 G4int ntupleId, G4int columnId, const G4Stri 345 G4int ntupleId, G4int columnId, const G4String& value) 318 { 346 { 319 return FillNtupleTColumn<std::string>(ntuple 347 return FillNtupleTColumn<std::string>(ntupleId, columnId, value); 320 } << 348 } 321 349 322 //____________________________________________ 350 //_____________________________________________________________________________ 323 G4bool G4RootPNtupleManager::AddNtupleRow(G4in 351 G4bool G4RootPNtupleManager::AddNtupleRow(G4int ntupleId) 324 { << 352 { 325 if ( fState.GetIsActivation() && ( ! GetActi 353 if ( fState.GetIsActivation() && ( ! GetActivation(ntupleId) ) ) { 326 //G4cout << "Skipping AddNtupleRow for " < << 354 //G4cout << "Skipping AddNtupleRow for " << ntupleId << G4endl; 327 return false; << 355 return false; 328 } << 356 } 329 << 357 330 if ( IsVerbose(kVL4) ) { << 358 #ifdef G4VERBOSE 331 Message(kVL4, "add", "pntuple row", " ntup << 359 if ( fState.GetVerboseL4() ) { 332 } << 360 G4ExceptionDescription description; 333 << 361 description << " ntupleId " << ntupleId; 334 // Creating ntuples on workers is triggered << 362 fState.GetVerboseL4()->Message("add", "pntuple row", description); 335 // or AddRow (in only columns of vector type << 363 } 336 CreateNtuplesIfNeeded(); << 364 #endif 337 365 338 auto ntupleDescription = GetNtupleDescriptio 366 auto ntupleDescription = GetNtupleDescriptionInFunction(ntupleId, "AddNtupleRow"); 339 if (ntupleDescription == nullptr) return fal << 367 if ( ! ntupleDescription ) return false; 340 << 368 341 auto rfile = std::get<0>(*ntupleDescription- << 369 G4AutoLock lock(&addRowMutex); 342 << 343 G4AutoLock lock(&pntupleMutex); << 344 lock.unlock(); << 345 mutex toolsLock(lock); 370 mutex toolsLock(lock); 346 auto result << 371 auto result 347 = ntupleDescription->GetNtuple()->add_row( << 372 = ntupleDescription->fNtuple >> 373 ->add_row(toolsLock, *ntupleDescription->fFile); 348 374 349 if ( ! result ) { 375 if ( ! result ) { 350 Warn("NtupleId " + to_string(ntupleId) + " << 376 G4ExceptionDescription description; 351 fkClass, "AddNtupleRow"); << 377 description << " " << " ntupleId " << ntupleId 352 } << 378 << "adding row has failed."; 353 << 379 G4Exception("G4RootPNtupleManager::AddNtupleRow()", 354 ntupleDescription->GetDescription().SetHasFi << 380 "Analysis_W002", JustWarning, description); 355 << 381 } 356 if ( IsVerbose(kVL3) ) { << 382 357 Message(kVL3, "add", "pntuple row", " ntup << 383 #ifdef G4VERBOSE 358 } << 384 if ( fState.GetVerboseL3() ) { 359 << 385 G4ExceptionDescription description; >> 386 description << " ntupleId " << ntupleId; >> 387 fState.GetVerboseL3()->Message("add", "pntuple row", description); >> 388 } >> 389 #endif 360 390 361 return true; 391 return true; 362 } 392 } 363 393 364 //____________________________________________ 394 //_____________________________________________________________________________ 365 G4bool G4RootPNtupleManager::Merge() 395 G4bool G4RootPNtupleManager::Merge() 366 { 396 { 367 for ( auto ntupleDescription : fNtupleDescri 397 for ( auto ntupleDescription : fNtupleDescriptionVector) { 368 398 369 // skip inactivated ntuples 399 // skip inactivated ntuples 370 if (! ntupleDescription->GetDescription(). << 400 if ( ! ntupleDescription->fActivation ) continue; 371 (ntupleDescription->GetNtuple() == nul << 401 372 // G4cout << "skipping inactive ntuple " << 402 #ifdef G4VERBOSE 373 continue; << 403 if ( fState.GetVerboseL4() ) { 374 } << 404 fState.GetVerboseL4() 375 << 405 ->Message("merge", "pntuple", ntupleDescription->fNtupleBooking.name()); 376 if ( IsVerbose(kVL4) ) { << 406 } 377 Message(kVL4, "merge", "pntuple", << 407 #endif 378 ntupleDescription->GetDescription().Ge << 408 379 } << 409 G4AutoLock lock(&endFillMutex); 380 << 381 auto rfile = std::get<0>(*ntupleDescriptio << 382 << 383 G4AutoLock lock(&pntupleMutex); << 384 lock.unlock(); << 385 mutex toolsLock(lock); 410 mutex toolsLock(lock); 386 auto result << 411 auto result 387 = ntupleDescription->GetNtuple()->end_fi << 412 = ntupleDescription->fNtuple >> 413 ->end_fill(toolsLock, *ntupleDescription->fFile); 388 414 389 if ( ! result ) { 415 if ( ! result ) { 390 Warn("Ntuple " + ntupleDescription->GetD << 416 G4ExceptionDescription description; 391 "end fill has failed.", fkClass, "M << 417 description << " " << " ntuple " << ntupleDescription->fNtupleBooking.name() 392 } << 418 << "end fill has failed."; 393 << 419 G4Exception("G4RootPNtupleManager::Merge()", 394 if ( IsVerbose(kVL3) ) { << 420 "Analysis_W002", JustWarning, description); 395 Message(kVL3, "merge", "pntuple", << 396 ntupleDescription->GetDescription().Ge << 397 } 421 } 398 422 >> 423 delete ntupleDescription->fNtuple; >> 424 ntupleDescription->fNtuple = nullptr; >> 425 >> 426 #ifdef G4VERBOSE >> 427 if ( fState.GetVerboseL3() ) { >> 428 fState.GetVerboseL3() >> 429 ->Message("merge", "pntuple", ntupleDescription->fNtupleBooking.name()); >> 430 } >> 431 #endif 399 } 432 } 400 << 401 // Set new cycle << 402 fNewCycle = true; << 403 << 404 return true; 433 return true; 405 } << 406 << 407 //____________________________________________ << 408 G4bool G4RootPNtupleManager::Reset() << 409 { << 410 // Reset ntuple description, this will delet << 411 // we have its ownership. << 412 // The ntuples will be recreated with new cy << 413 434 414 for ( auto ntupleDescription : fNtupleDescri << 415 ntupleDescription->Reset(); << 416 } << 417 << 418 fNtupleVector.clear(); << 419 << 420 return true; << 421 } 435 } 422 436 423 //____________________________________________ 437 //_____________________________________________________________________________ 424 void G4RootPNtupleManager::Clear() << 438 G4bool G4RootPNtupleManager::Reset(G4bool deleteNtuple) 425 { 439 { 426 for ( auto ntupleDescription : fNtupleDescri 440 for ( auto ntupleDescription : fNtupleDescriptionVector ) { 427 delete ntupleDescription->GetNtuple(); << 441 if ( deleteNtuple ) { 428 } << 442 delete ntupleDescription->fNtuple; 429 << 443 } 430 fNtupleDescriptionVector.clear(); << 444 ntupleDescription->fNtuple = nullptr; 431 fNtupleVector.clear(); << 432 << 433 Message(kVL2, "clear", "pntuples"); << 434 } << 435 << 436 //____________________________________________ << 437 G4bool G4RootPNtupleManager::Delete(G4int id) << 438 { << 439 if ( IsVerbose(G4Analysis::kVL4) ) { << 440 Message(G4Analysis::kVL4, "delete", "pntup << 441 } 445 } 442 446 443 auto ntupleDescription = GetNtupleDescriptio << 447 fNtupleVector.clear(); 444 << 448 445 if (ntupleDescription == nullptr) return fal << 446 << 447 // Delete/clear ntuple data << 448 delete ntupleDescription->GetNtuple(); << 449 ntupleDescription->SetNtuple(nullptr); << 450 ntupleDescription->SetBasePNtuple(nullptr); << 451 ntupleDescription->GetMainBranches().clear() << 452 << 453 // Update ntuple vector << 454 auto index = id - GetFirstId(); << 455 fNtupleVector[index] = nullptr; << 456 << 457 Message(G4Analysis::kVL2, "delete", "pntuple << 458 << 459 return true; 449 return true; 460 } << 450 } 461 451 462 //____________________________________________ 452 //_____________________________________________________________________________ 463 453 464 void G4RootPNtupleManager::SetActivation( 454 void G4RootPNtupleManager::SetActivation( 465 G4bool activation) 455 G4bool activation) 466 { 456 { 467 for ( auto ntupleDescription : fNtupleDescri 457 for ( auto ntupleDescription : fNtupleDescriptionVector ) { 468 ntupleDescription->GetDescription().SetAct << 458 ntupleDescription->fActivation = activation; 469 } << 459 } 470 } 460 } 471 461 472 //____________________________________________ 462 //_____________________________________________________________________________ 473 463 474 void G4RootPNtupleManager::SetActivation( 464 void G4RootPNtupleManager::SetActivation( 475 G4int ntupleId, G4bool activation) 465 G4int ntupleId, G4bool activation) 476 { 466 { 477 auto ntupleDescription = GetNtupleDescriptio 467 auto ntupleDescription = GetNtupleDescriptionInFunction(ntupleId, "SetActivation"); 478 if (ntupleDescription == nullptr) return; << 468 if ( ! ntupleDescription ) return; 479 469 480 ntupleDescription->GetDescription().SetActiv << 470 ntupleDescription->fActivation = activation; 481 } 471 } 482 472 483 //____________________________________________ 473 //_____________________________________________________________________________ 484 G4bool G4RootPNtupleManager::GetActivation( 474 G4bool G4RootPNtupleManager::GetActivation( 485 G4int ntupleId) const 475 G4int ntupleId) const 486 { 476 { 487 auto ntupleDescription = GetNtupleDescriptio 477 auto ntupleDescription = GetNtupleDescriptionInFunction(ntupleId, "GetActivation"); 488 if (ntupleDescription == nullptr) return fal << 478 if ( ! ntupleDescription ) return false; 489 479 490 return ntupleDescription->GetDescription().G << 480 return ntupleDescription->fActivation; 491 } 481 } 492 482 493 //____________________________________________ 483 //_____________________________________________________________________________ 494 void G4RootPNtupleManager::SetNewCycle(G4bool << 484 G4int G4RootPNtupleManager::GetNofNtuples() const 495 { 485 { 496 fNewCycle = value; << 486 return fNtupleVector.size(); 497 } 487 } 498 488 499 //____________________________________________ 489 //_____________________________________________________________________________ 500 G4bool G4RootPNtupleManager::GetNewCycle() con << 490 G4int G4RootPNtupleManager::GetNofNtupleBookings() const 501 { 491 { 502 return fNewCycle; << 492 return fNtupleDescriptionVector.size(); 503 } 493 } 504 494 505 //____________________________________________ 495 //_____________________________________________________________________________ 506 void G4RootPNtupleManager::SetNtupleRowWise(G4 << 496 G4bool G4RootPNtupleManager::IsEmpty() const 507 { 497 { 508 fRowWise = rowWise; << 498 return ! fNtupleDescriptionVector.size(); 509 fRowMode = rowMode; << 499 } 510 } << 500 511 501