35{
37 const std::string& treeName)
38 {
42 (worker->getAlg ("NTupleSvc_" + outputStream + "_" + treeName));
43 if (result == 0)
44 {
46 (worker->getAlg ("NTupleSvc_" + outputStream));
47 }
50 }
51
52
53
54 void NTupleSvc ::
55 testInvariant () const
56 {}
57
58
59
60 NTupleSvc ::
61 NTupleSvc (const std::string& val_outputName)
62 : m_file (0),
m_tree (0), m_initialized (false),
63 m_whiteboard (0)
64 {
66
67 m_outputName = val_outputName;
68
70 }
71
72
73
74 NTupleSvc ::
75 ~NTupleSvc ()
76 {
78 }
79
80
81
82 void NTupleSvc ::
83 copyBranch (const std::string& name)
84 {
86 m_copyBranches.insert (name);
87 }
88
89
90
91 void NTupleSvc ::
92 copyBranchList (const std::string& fileName)
93 {
94
95
98 while (getline (
file, line))
99 {
100 while (!
line.empty() && isspace (line[0]))
102 while (!
line.empty() && isspace (line[
line.size()-1]))
104 if (!
line.empty() && line[0] !=
'#')
105 copyBranch (line);
106 }
107 }
108
109
110
111 void NTupleSvc ::
112 addWhiteFloat (const std::string& varName)
113 {
115 m_whiteFloat.insert (varName);
116 }
117
118
119
120 void NTupleSvc ::
121 addWhiteArray (const std::string& varName)
122 {
124 m_whiteArray.insert (varName);
125 }
126
127
128
129 TTree *NTupleSvc ::
130 tree () const
131 {
135 }
136
137
138
139 bool NTupleSvc ::
140 getFilterPassed () const
141 {
143 return m_taken;
144 }
145
146
147
148 void NTupleSvc ::
149 setFilterPassed (
bool passed)
150 {
153 m_taken = true;
154 }
155
156
157
158 const std::string& NTupleSvc ::
159 treeName () const
160 {
162 return m_treeName;
163 }
164
165
166
167 void NTupleSvc ::
168 treeName (const std::string& val_treeName)
169 {
171 m_treeName = val_treeName;
172 }
173
174
175
176 const char *NTupleSvc ::
177 GetName () const
178 {
180 return m_outputName.c_str();
181 }
182
183
184
186 setupJob (Job& job)
187 {
189 RCU_REQUIRE2_SOFT (
job.outputHas (m_outputName), (
"output stream " + m_outputName +
" not configured. try:\n EL::OutputStream output (\"" + m_outputName +
"\");\n job.addOutput (output);").c_str());
190 return EL::StatusCode::SUCCESS;
191 }
192
193
194
196 {
198
199 m_connected = false;
200 return EL::StatusCode::SUCCESS;
201 }
202
203
204
206 {
208
209 m_file = wk()->getOutputFile (m_outputName);
210 std::string
name = m_treeName;
211 if (
name.empty())
name = wk()->tree()->GetName();
213 try
214 {
215 m_file->cd ();
216 m_tree =
new TTree (
name.c_str(), m_tree_title.c_str());
217 curDir->cd ();
218 } catch (...)
219 {
220 curDir->cd ();
221 }
222
223
224 m_tree->SetAutoSave(10000);
225
226 m_tree->SetAutoFlush( -30000000 );
227 TTree::SetBranchStyle(1);
228
229 return EL::StatusCode::SUCCESS;
230 }
231
232
233
235 {
237
238 m_taken = false;
239 return EL::StatusCode::SUCCESS;
240 }
241
242
243
245 {
247
248 initBranches ();
249
250 if (!m_taken)
251 return EL::StatusCode::SUCCESS;
252
253 copyInput ();
254
255 for (whiteInfoMIter iter = m_whiteInfo.begin(),
256 end = m_whiteInfo.end(); iter != end; ++ iter)
257 {
259 {
262 m_whiteboard->getArray (
iter->name,
size, values);
263 std::vector<float>(values,values+
size).swap (
iter->buffer);
264 } else
265 iter->buffer[0] = m_whiteboard->getFloat (
iter->name);
266 }
267
269 return EL::StatusCode::SUCCESS;
270 }
271
272
273
274 bool NTupleSvc ::
275 hasName (const std::string& name) const
276 {
278 return
279 name ==
"NTupleSvc_" + m_outputName ||
280 name ==
"NTupleSvc_" + m_outputName +
"_" + m_treeName;
281 }
282
283
284
285 void NTupleSvc ::
286 initBranches ()
287 {
288 if (m_initialized == false)
289 {
290 m_initialized = true;
291
292 std::set<std::string> branchList;
293
294 findBranches (branchList);
295 initOutput (branchList);
296
297 for (m_whiteFloatIter iter = m_whiteFloat.begin(),
298 end = m_whiteFloat.end(); iter != end; ++ iter)
299 {
303 m_whiteInfo.push_back (info);
304 }
305 for (m_whiteArrayIter iter = m_whiteArray.begin(),
306 end = m_whiteArray.end(); iter != end; ++ iter)
307 {
311 m_whiteInfo.push_back (info);
312 }
313 for (whiteInfoMIter iter = m_whiteInfo.begin(),
314 end = m_whiteInfo.end(); iter != end; ++ iter)
315 {
317 {
320 } else
321 {
322 iter->buffer.resize (1);
324 }
325 }
326 if (!m_whiteInfo.empty())
328 }
329 }
330
331
332 void NTupleSvc ::
333 findBranches (std::set<std::string>& branchList)
334 {
335 for (m_copyBranchesIter iter = m_copyBranches.begin(),
336 end = m_copyBranches.end(); iter != end; ++ iter)
337 {
338 std::size_t
count = 0;
340 TObject *object = 0;
341
342 for (TIter branchIter (wk()->
tree()->GetListOfBranches());
343 (object = branchIter());)
344 {
346 Ssiz_t len = 0;
347
349 {
350 branchList.insert (
str.Data());
352 }
353 }
355 throw std::runtime_error ("could not find any branch that matches pattern \"" + *iter + "\"");
356 }
357 }
358
359
360
361 void NTupleSvc ::
362 initOutput (const std::string& branchName)
363 {
364
365 for (copyInfoMIter branch = m_copyInfo.begin(),
366 end = m_copyInfo.end(); branch != end; ++ branch)
367 {
368 if (branch->name == branchName)
369 return;
370 }
371
373 info.name = branchName;
374 info.source = wk()->tree()->FindBranch (branchName.c_str());
375 if (
info.source == 0)
376 throw std::runtime_error ("could not find input branch: " + branchName);
377
378 const char *className =
info.source->GetClassName();
379 if (strlen (className) > 0)
380 {
381 info.target =
m_tree->Branch (branchName.c_str(), className,
382 static_cast<void*>(0));
383 } else
384 {
385 static std::map<std::string,std::string>
types;
387 {
388 types[
"Char_t"] =
"B";
389 types[
"UChar_t"] =
"b";
390 types[
"Short_t"] =
"S";
391 types[
"UShort_t"] =
"s";
392 types[
"Int_t"] =
"I";
393 types[
"UInt_t"] =
"i";
394 types[
"Float_t"] =
"F";
395 types[
"Double_t"] =
"D";
396 types[
"Long64_t"] =
"L";
397 types[
"ULong64_t"] =
"l";
398 types[
"Bool_t"] =
"O";
399 }
400
401 std::string leaves;
403 for (TIter iter =
info.source->GetListOfLeaves(); (
object =
iter()); )
404 {
405 TLeaf *myleaf =
dynamic_cast<TLeaf*
>(
object);
406 if (myleaf == 0)
407 throw std::runtime_error ("found non-leaf object in leaf list");
408
409 std::string
typeName = myleaf->GetTypeName();
410 std::map<std::string,std::string>::const_iterator
type
411 =
types.find (typeName);
413 throw std::runtime_error ("unknown leaf type " + typeName);
414
415 if (!leaves.empty())
416 leaves += ":";
417 leaves = leaves + myleaf->GetTitle() +
"/" +
type->second;
418 }
419 if (leaves.empty())
420 throw std::runtime_error ("failed to scan leaves of branch " + branchName);
421
422 for (std::string::size_type pos = 0;
423 (
pos = leaves.find (
"[", pos)) != std::string::npos; )
424 {
426 std::string::size_type pos2 = leaves.find ("]", pos);
427 if (pos2 == std::string::npos)
428 throw std::runtime_error ("failed to scan leaf dimensions for " + leaves);
429 std::string
dim = leaves.substr (pos, pos2 - pos);
430 if (!(dim[0] >= '0' && dim[0] <= '9'))
431 initOutput (dim);
432 }
433 info.target =
m_tree->Branch (branchName.c_str(),
static_cast<void*
>(0),
434 leaves.c_str());
435 }
436 m_copyInfo.push_back (info);
437 }
438
439
440
441 void NTupleSvc ::
442 initOutput (const std::set<std::string>& branchList)
443 {
444 for (std::set<std::string>::const_iterator branch = branchList.begin(),
445 end = branchList.end(); branch != end; ++ branch)
446 initOutput (*branch);
447 }
448
449
450
451 void NTupleSvc ::
452 copyInput ()
453 {
454 if (!m_connected)
455 {
456 for (copyInfoMIter info = m_copyInfo.begin(),
457 end = m_copyInfo.end(); info != end; ++ info)
458 {
459 info->source =
dynamic_cast<TBranch*
>
460 (wk()->tree()->GetBranch (
info->name.c_str()));
462 }
463 m_connected = true;
464 }
465
466 for (copyInfoMIter info = m_copyInfo.begin(),
467 end = m_copyInfo.end(); info != end; ++ info)
468 {
469 void *address =
info->source->GetAddress();
470 if (address == 0)
471 {
472 std::size_t
size =
sizeof (
void*);
474 for (TIter iter =
info->source->GetListOfLeaves();
476 {
477 TLeaf *myleaf =
dynamic_cast<TLeaf*
>(
object);
479 Int_t countval;
480 TLeaf *countleaf = myleaf->GetLeafCounter (countval);
481 if (countleaf)
482 countval = countleaf->GetMaximum();
483 if (countval < 0)
484 throw std::runtime_error (std::format (
"could not determine size of leaf {} in branch {}", myleaf->GetName(),
info->name));
485 if (countval == 0)
486 countval = 1;
487 const std::size_t mysize
488 = myleaf->GetOffset() + myleaf->GetLenType() * countval;
491 }
493 info->source->SetStatus (1);
494 info->source->SetAddress (address = &
info->buffer[0]);
495 }
497 info->target->SetAddress (address);
498 info->source->GetEntry (wk()->treeEntry(), 1);
499 }
500 }
501}
#define RCU_DESTROY_INVARIANT(x)
#define RCU_ASSERT2_SOFT(x, y)
#define RCU_CHANGE_INVARIANT(x)
#define RCU_REQUIRE2_SOFT(x, y)
#define RCU_NEW_INVARIANT(x)
#define RCU_REQUIRE_SOFT(x)
#define RCU_READ_INVARIANT(x)
static const std::vector< std::string > types
size_t size() const
Number of registered mappings.
int count(std::string s, const std::string ®x)
count how many occurances of a regx are in a string
ID3PD * m_tree
Pointer to the ID3PD object used.
NTupleSvc * getNTupleSvc(IWorker *worker, const std::string &outputStream, const std::string &treeName="")
effects: get the skimming algorithm for the given output for this worker guarantee: strong failures: ...
::StatusCode StatusCode
StatusCode definition for legacy code.
WhiteBoardSvc * getWhiteBoardSvc(IWorker *worker)
effects: get the whiteboard service for this worker guarantee: strong failures: formula service not c...