FairRoot/PandaRoot
PndFilteredPrimaryGenerator.cxx
Go to the documentation of this file.
2 
3 #include "FairGenericStack.h" // for FairGenericStack
4 #include "FairMCEventHeader.h" // for FairMCEventHeader
5 
6 #include "TDatabasePDG.h"
7 #include "TObjArray.h"
8 #include "TObjString.h"
9 #include "TClonesArray.h"
10 #include "TParticle.h"
11 
12 
13 // -------------------------------------------------------------------------
14 
16 : FairPrimaryGenerator(),
17 
18  fEvtFilterStat(FairEvtFilterParams()),
19  fVerbose(3),
20  fEventNrFiltered(0),
21  fEventPrintFreq(100)
22 {
23  fdbPdg = TDatabasePDG::Instance();
24 
25  std::vector<TString> tmpfPartNames = {"e+", "e-", "mu+", "mu-", "pi+", "pi-", "k+", "k-", "p+", "p-", "n0", "n0b", "e+-", "mu+-", "pi+-", "k+-", "p+-", "n00b" , "t+", "t-", "t+-", "nt", "any" };
26  std::vector<int> tmpfNamePdg = {-11 , 11 , -13 , 13 , 211 , -211 , 321 , -321, 2212, -2212, 2112, -2112, 11000 , 13000 , 211000 , 321000 , 2212000, 2112000, 1 , -1 , 2 , 0 , 3 };
27  std::vector<int> tmpfCombFsPdg = {-11 , 11 , -13 , 13 , 211 , -211 , 321 , -321, 2212, -2212 , 22};
28 
29  // initialize sets and vectors with names and codes
30  fPartNames = tmpfPartNames;
31  fNamePdg = tmpfNamePdg;
32  fCombFsPdg = tmpfCombFsPdg;
33 
34  std::unordered_set<int> tmpfSetFsPdg(fCombFsPdg.begin(), fCombFsPdg.end());
35  fSetFsPdg = tmpfSetFsPdg;
36 
37  // initialize maps between names and codes
38  for (int i=0;i<(int)fPartNames.size();++i) fNameCodeMap[fPartNames[i]] = fNamePdg[i];
39  for (int i=0;i<(int)fPartNames.size();++i) fCodeNameMap[fNamePdg[i]] = fPartNames[i];
40 }
41 
42 // -------------------------------------------------------------------------
43 
45 : FairPrimaryGenerator(),
46 
47  fEvtFilterStat(FairEvtFilterParams()),
48  fVerbose(3),
49  fEventNrFiltered(0),
50  fEventPrintFreq(100)
51 {
52  fdbPdg = TDatabasePDG::Instance();
53 
54  std::vector<TString> tmpfPartNames = {"e+", "e-", "mu+", "mu-", "pi+", "pi-", "k+", "k-", "p+", "p-", "n0", "n0b", "e+-", "mu+-", "pi+-", "k+-", "p+-", "n00b" , "t+", "t-", "t+-", "nt", "any" };
55  std::vector<int> tmpfNamePdg = {-11 , 11 , -13 , 13 , 211 , -211 , 321 , -321, 2212, -2212, 2112, -2112, 11000 , 13000 , 211000 , 321000 , 2212000, 2112000, 1 , -1 , 2 , 0 , 3 };
56  std::vector<int> tmpfCombFsPdg = {-11 , 11 , -13 , 13 , 211 , -211 , 321 , -321, 2212, -2212 , 22};
57 
58  // initialize sets and vectors with names and codes
59  fPartNames = tmpfPartNames;
60  fNamePdg = tmpfNamePdg;
61  fCombFsPdg = tmpfCombFsPdg;
62 
63  std::unordered_set<int> tmpfSetFsPdg(fCombFsPdg.begin(), fCombFsPdg.end());
64  fSetFsPdg = tmpfSetFsPdg;
65 
66  // initialize maps between names and codes
67  for (int i=0;i<(int)fPartNames.size();++i) fNameCodeMap[fPartNames[i]] = fNamePdg[i];
68  for (int i=0;i<(int)fPartNames.size();++i) fCodeNameMap[fNamePdg[i]] = fPartNames[i];
69 
70  AddFilter(filterset);
71 }
72 
73 // -------------------------------------------------------------------------
74 
76 {
78 
79  if (fVerbose)
80  for (int ifs = 0; ifs < (int)fFilterSets.size(); ++ifs)
81  {
82  cout <<"FILTER SET "<< ifs<<endl<<endl;
83  for (int i = 0; i < (int)fFilterSets[ifs].size(); ++i) fFilterSets[ifs][i].Print();
84  cout <<endl;
85  }
86 
87  return kTRUE;
88 }
89 
90 // --------------------------------------------------------------------
91 
93 {
94  StrVec toks;
95  TObjArray *tok = s.Tokenize(delim);
96  int N = tok->GetEntries();
97  for (int i=0;i<N;++i)
98  {
99  TString token = (((TObjString*)tok->At(i))->String()).Strip(TString::kBoth);
100  toks.push_back(token);
101  }
102  return toks;
103 }
104 
105 // --------------------------------------------------------------------
106 
107 bool PndFilteredPrimaryGenerator::CheckKinematic(const PndSmpFilt &f, const TLorentzVector &p4)
108 {
109  bool acc_trk = true;
110 
111  double curr_p = p4.P(); acc_trk = (curr_p >= f.pmin && curr_p <= f.pmax);
112  if (acc_trk) { double curr_pt = p4.Pt(); acc_trk = (curr_pt >= f.ptmin && curr_pt <= f.ptmax); }
113  if (acc_trk) { double curr_pz = p4.Pz(); acc_trk = (curr_pz >= f.pzmin && curr_pz <= f.pzmax); }
114  if (acc_trk) { double curr_tht = p4.Theta()*57.2958; acc_trk = (curr_tht >= f.thtmin && curr_tht <= f.thtmax); }
115  if (acc_trk) { double curr_phi = p4.Phi()*57.2958; acc_trk = (curr_phi >= f.phimin && curr_phi <= f.phimax); }
116 
117  return acc_trk;
118 }
119 
120 // --------------------------------------------------------------------
121 
123 {
124  if (fdbPdg->GetParticle(pdg)!=0x0 && fdbPdg->GetParticle(pdg)->AntiParticle()!=0x0)
125  return fdbPdg->GetParticle(pdg)->AntiParticle()->PdgCode();
126 
127  return pdg;
128 }
129 
130 // --------------------------------------------------------------------
131 
132 void PndFilteredPrimaryGenerator::GetRangeDouble(TString s, double &a, double &b, TString delim, bool forceset)
133 {
134  int len = delim.Length();
135  a = (TString(s(0,s.Index(delim)))).Atof();
136  double tmpb = (TString(s(s.Index(delim)+len,10000))).Atof();
137  if (tmpb>0. || forceset) b = tmpb;
138 }
139 
140 // --------------------------------------------------------------------
141 
143 {
144  int len = delim.Length();
145  a = (TString(s(0,s.Index(delim)))).Atoi();
146  int tmpb = (TString(s(s.Index(delim)+len,10000))).Atoi();
147  if (tmpb>0) b=tmpb;
148 }
149 
150 
151 
152 // -------------------------------------------------------------------------
153 // Parses the definition string for a filter
154 // It may be provided a string of the form 'Filt_1.1 && Filt_1.2 || Filt_2.1 || Filt_3.1 && Filt_3.2 && Filt_3.2'
155 // where && (AND) has higher priority than || (OR)
156 
158 {
159  // some replacements
160  filterStr.ToLower();
161  filterStr.ReplaceAll(":","&&");
162  filterStr.ReplaceAll("gamma","nt");
163  filterStr.ReplaceAll("gam","nt");
164  filterStr.ReplaceAll("ch0","nt");
165  filterStr.ReplaceAll("tr","t");
166  filterStr.ReplaceAll("ch","t");
167  filterStr.ReplaceAll("mass","m");
168 
169 
170  // split filter string
171  StrVec filtersets_str = SplitString(filterStr,"||");
172 
173  // *** loop over event type filters (the filter sets)
174  for (int ifs=0; ifs < (int) filtersets_str.size(); ++ ifs)
175  {
176  StrVec filters_str = SplitString(filtersets_str[ifs],"&&");
177 
178  // --------------------
179  // parse filter strings
180  // --------------------
181 
182  PndSmpFilterSet filters;
183 
184  for (int i=0;i<(int) filters_str.size();++i)
185  {
186  // some filter checks
187  TString fs = filters_str[i];
188  if ( (!fs.EndsWith(")")) || (fs.Contains(",") && !fs.Contains("[")) )
189  {
190  cout <<" --> Please check filter string '"<<fs<<"'"<<endl;
191  exit(0);
192  }
193 
194  // a copy without the X() stuff
195  TString tmpfs = fs(fs.Index("(")+1,fs.Length()-fs.Index("(")-2);
196 
197  StrVec cuts = SplitString(tmpfs,";");
198 
199  if (fVerbose>3) cout<<endl<<fs<<endl<<tmpfs<<endl;
200 
201  PndSmpFilt f;
202  f.name = fs;
203 
204  // negate filter?
205  if (fs.BeginsWith("!")) {f.veto = true; fs.ReplaceAll("!","");}
206 
207  // if the filter string has the form "M(...)" it's a mass filter, else a multiplicity filter ("(...)")
208  if (fs.BeginsWith("m(")) f.compo=true;
209 
210  for (int j=0;j<(int)cuts.size();++j)
211  {
212  TString ct = cuts[j];
213  //cout <<" "<<ct<<endl;
214 
215  // if specifier (p, tht, pt, ...) store it and remove the '[]'
216  TString key = "";
217  if (ct.Contains("["))
218  {
219  key = ct(0,ct.Index("["));
220  ct = ct(ct.Index("[")+1,ct.Length()-ct.Index("[")-2);
221  }
222 
223  // either multiplicity or particle names
224  if (key=="")
225  {
226  // mult, either range delimiter '..' found
227  if (ct.Contains("..")) GetRangeInt(ct, f.nmin, f.nmax);
228  // or single number, explicitely allowed to be 0 (kind of veto filtering)
229  else if (ct.Atoi()!=0 || ct=="0") f.nmin = f.nmax = ct.Atoi();
230  // particle name of the particle to be counted or a list of particles for inv. mass filter (in case f.compo = true)
231  else
232  {
233  StrVec parts = SplitString(ct);
234  for (int jj=0;jj<(int)parts.size();++jj)
235  {
236  if (fNameCodeMap.find(parts[jj])!=fNameCodeMap.end() && f.ndau<5) f.pdg[f.ndau++] = fNameCodeMap[parts[jj]];
237 
238  // the key word 'nocc' prevents automatic charged conjugates for
239  if (parts[jj]=="nocc") f.nocc = true;
240  }
241  for (int jj=0;jj<(int)parts.size();++jj) if (f.pdg[jj]==0) f.pdg[jj] = 22;
242  }
243  }
244 
245  // other pdg code
246  else if (key=="pdg") {f.pdg[0] = ct.Atoi(); f.ndau=1;}
247 
248  // kinematic ranges
249  else if (key=="p") GetRangeDouble(ct, f.pmin, f.pmax);
250  else if (key=="pt") GetRangeDouble(ct, f.ptmin, f.ptmax);
251  else if (key=="pz") GetRangeDouble(ct, f.pzmin, f.pzmax);
252  else if (key=="tht") GetRangeDouble(ct, f.thtmin, f.thtmax);
253  else if (key=="phi") GetRangeDouble(ct, f.phimin, f.phimax, ",", 1);
254  else if (key=="m") GetRangeDouble(ct, f.mcntr, f.mwin);
255  }
256 
257  if ( (f.compo && f.ndau<2) || (!f.compo && f.ndau!=1))
258  {
259  cout <<" --> Please check filter string '"<<fs<<"'"<<endl;
260  exit(0);
261  }
262  else filters.push_back(f);
263  }
264 
265  fFilterSets.push_back(filters);
266  }
267 }
268 
269 
270 // -------------------------------------------------------------------------
271 
273 {
275 
276  //-------------
277  for (int i0=0; i0<(int)l0->size(); ++i0)
278  {
279  PndSmpCand &c0 = (*l0)[i0];
280 
281  // if l0 == l1, start at i1 = i0+1 to avoid double counting
282  int st1 = 0;
283  if ((*l1) == (*l0)) st1 = i0+1;
284 
285  // -------------
286  for (int i1=st1; i1<(int)l1->size(); ++i1)
287  {
288  PndSmpCand &c1 = (*l1)[i1];
289  if (c1.Overlap(c0)) continue;
290 
291  // only two lists? done!
292  if (l2==0) res.push_back(PndSmpCand(pdg, c0, c1));
293  else
294  {
295  // if l2 == l0 or l1, start at i2 = i0/i1+1 to avoid double counting
296  int st2 = 0;
297  if (*l2==*l1) st2 = i1+1;
298  else if (*l2==*l0) st2 = i0+1;
299 
300  // -------------
301  for (int i2=st2; i2<(int)l2->size(); ++i2)
302  {
303  PndSmpCand &c2 = (*l2)[i2];
304  if (c2.Overlap(c1) || c2.Overlap(c0)) continue;
305 
306  // only three lists? done!
307  if (l3==0) res.push_back(PndSmpCand(pdg, c0, c1, c2));
308  else
309  {
310  // if l3 == l0, l1 or l2, start at i3 = i0/i1/i2+1 to avoid double counting
311  int st3 = 0;
312  if (*l3==*l2) st3 = i2+1;
313  else if (*l3==*l1) st3 = i1+1;
314  else if (*l3==*l0) st3 = i0+1;
315 
316  // -------------
317  for (int i3=st3; i3<(int)l3->size(); ++i3)
318  {
319  PndSmpCand &c3 = (*l3)[i3];
320  if (c3.Overlap(c2) || c3.Overlap(c1) || c3.Overlap(c0)) continue;
321 
322  // only four lists? done!
323  if (l4==0) res.push_back(PndSmpCand(pdg, c0, c1, c2, c3));
324  else
325  {
326  // if l3 == l0, l1 or l2, start at i3 = i0/i1/i2+1 to avoid double counting
327  int st4 = 0;
328  if (*l4==*l3) st4 = i3+1;
329  else if (*l4==*l2) st3 = i2+1;
330  else if (*l4==*l1) st3 = i1+1;
331  else if (*l4==*l0) st3 = i0+1;
332 
333  // -------------
334  for (int i4=st4; i4<(int)l4->size(); ++i4)
335  {
336  PndSmpCand &c4 = (*l4)[i4];
337  if (c4.Overlap(c3) || c4.Overlap(c2) || c4.Overlap(c1) || c4.Overlap(c0)) continue;
338 
339  res.push_back(PndSmpCand(pdg, c0, c1, c2, c3, c4));
340  } // for i4
341  } // else i3
342  } // for i3
343  } // else i2
344  } // for i2
345  } // else i1
346  } // for i1
347  } // for i0
348 
349  return res;
350 }
351 
352 // --------------------------------------------------------------------
353 
355 {
356  printf("LIST %s with %d candidates\n",name.Data(), (int)l.size());
357  for (int i=0;i<(int)l.size(); ++i) {printf(" %2d : ",i); l[i].Print();}
358 }
359 
360 
361 // --------------------------------------------------------------------
362 // ----- Public method GenerateEvent -----------------------------------
363 
365 {
366  Int_t iTry = 0; // number of attempts to find the next event that suits your filter
367 
368  bool acc_glob = false; // is kTRUE if the event is finally accepted
369 
370  bool active_filters = (fFilterSets.size()>0);
371 
372  while( !acc_glob && iTry < fEvtFilterStat.fFilterMaxTries)
373  {
374  ++iTry; // count how often we run the generators before we accept an event
375  ++fEvtFilterStat.fGeneratedEvents; // total number of generated events
376 
377  pStack->Reset(); // Clean the stack
378  FairPrimaryGenerator::GenerateEvent(pStack); // fill the stack
379 
380  // no filtering --> accept event
381  if (!active_filters) {acc_glob = true; continue;}
382 
383  TClonesArray* fParticleList = pStack->GetListOfParticles();
384 
385 
386  fEventNr = fEventNrFiltered; // Fix event numbering in FairPrimaryGenerator (otherwise fRun will stop too early...)
387 
389 
390  // init all lists to empty list
391  std::map<int,PndSmpCandList> pdgList;
392  for (unsigned int i=0;i<fCombFsPdg.size();++i) pdgList[fCombFsPdg[i]] = all;
393 
394  int cnt = 0;
395 
396  // --------------
397  // Fill the lists
398  // --------------
399 
400  //for (int i=0;i<*nTrk;++i)
401  //{
402  for (Int_t iPart=0; iPart<fParticleList->GetEntries(); ++iPart)
403  {
404  TParticle *particle = (TParticle*)fParticleList->At(iPart);
405 
406  // the current MCT pdg code
407  Int_t pdg = particle->GetPdgCode();
408 
409  // do we want to count multiplicity for this code?
410  //if (set_mult_pdg.find(pdg)==set_mult_pdg.end()) continue;
411 
412  // is yes, create SmpCand
413  TLorentzVector l(particle->Px(), particle->Py(), particle->Pz(), particle->Energy());
414  Float_t ch = fdbPdg->GetParticle(pdg) ? fdbPdg->GetParticle(pdg)->Charge()/3. : 0;
415 
416  // and push to to all-list
417  if (fSetFsPdg.find(pdg)==fSetFsPdg.end())
418  {
419  // push to all list, but with uid = -1 for non-final states, since not needed for combinatorics
420  all.push_back(PndSmpCand(l, ch, pdg, -1));
421  continue;
422  }
423 
424  // create candidate with marker (uid >= 0) only for final states used for combinatorics
425  PndSmpCand sc(l, ch, pdg, cnt++);
426 
427  // and push to to all-list
428  all.push_back(sc);
429 
430  // add particle to all lists with the same charge
431  for (unsigned int j=0;j<fCombFsPdg.size();++j)
432  {
433  int pdg_ch = fdbPdg->GetParticle(fCombFsPdg[j])->Charge()/3.;
434  double pdg_m = fdbPdg->GetParticle(fCombFsPdg[j])->Mass();
435 
436  if (pdg_ch == (int)ch)
437  {
438  l.SetVectM(l.Vect(), pdg_m);
439  sc.SetP4(l);
440  pdgList[fCombFsPdg[j]].push_back(sc);
441  }
442  }
443  }
444 
445  // --------------
446  // print all lists
447  // --------------
448 
449  if (fVerbose>3)
450  {
451  PrintSmpCandList(all,"All particles:");
452 
453  if (fVerbose>4)
454  for (int i=0;i<(int)fCombFsPdg.size();++i)
455  {
456  int pdg = fCombFsPdg[i];
457  int nc = pdgList[pdg].size();
458  if (nc>0) PrintSmpCandList(pdgList[pdg],Form("%s",fCodeNameMap[pdg].Data()));
459  }
460  cout <<endl<<endl;
461  }
462 
463 
464  // -------------------
465  // Loop over filters
466  // -------------------
467 
468  acc_glob=false;
469 
470  for (int ifs=0; ifs < (int) fFilterSets.size(); ++ifs)
471  {
472  // did another filterset accept? then we don't need to check anymore
473  if (acc_glob) continue;
474 
475  // initialize filter set accept with true
476  bool acc_fset = true;
477 
478  // -------------------
479  // *** loop over count filters in filter set
480  // -------------------
481  for (int i=0; i<(int)fFilterSets[ifs].size(); ++i)
482  {
483  // if the event cannot be accepted anymore, skip the next filter test
484  if (!acc_fset) continue;
485 
486  // event accept flag
487  bool acc_evt = true;
488 
489  PndSmpFilt &f = fFilterSets[ifs][i];
490 
491  // if mass filter, skip here (first apply count filters, which are probably much faster)
492  if (f.compo) continue;
493 
494  int cnt_matches = 0;
495 
496  // *** loop over particles
497  for (int j=0 ; j<(int)all.size() ; ++j)
498  {
499  // *** check particle type first
500  //vector<TString> names = {"e+", "e-", "mu+", "mu-", "pi+", "pi-", "k+", "k-", "p+", "p-", "n0", "n0b", "e+-", "mu+-", "pi+-", "k+-", "p+-", "n" , "t+", "t-", "t+-", "nt", "any" };
501  //vector<int> name_pdg = {-11 , 11 , -13 , 13 , 211 , -211 , 321 , -321, 2212, -2212, 2112, -2112, 11000 , 13000 , 211000 , 321000 , 2212000, 2112000, 1 , -1 , 2 , 0 , 3 };
502 
503  // tracks pdg and charge
504  int trpdg = all[j].Pdg();
505  int trchg = (int) all[j].Charge();
506 
507  // filter pdg (or special) code
508  int flpdg = f.pdg[0];
509 
510  // the counters for any, t+-, t+, t- and nt/gam only for final states
511  if (all[j].Marker()>0)
512  {
513  // any particle: code = 3
514  if (flpdg == 3) trpdg = flpdg;
515 
516  // all charged tracks t+- : code = 2
517  if (flpdg == 2) trpdg = abs(trchg)*2;
518 
519  // simple track+- and neutral counting (t+,t-,nt) : code = charge (-1, +1, 0); 0 also used for photons with pdg = 22
520  if (abs(flpdg)<2) trpdg = trchg;
521  }
522 
523  // the pdg code ignoring charge : code = 1000*pdg, e.g. K+- = 321000, pi+- = 211000
524  if (flpdg%1000==0) trpdg = abs(trpdg)*1000;
525 
526  // *** check code and kinematic variables and count track
527  if ( (trpdg==flpdg) && CheckKinematic(f, all[j].P4()) )
528  {
529  cnt_matches++;
530  if (fVerbose>2) cout << "\033[1;34m ** ";
531  }
532  else if (fVerbose>2) cout << " ";
533 
534  // *** (and print if verbose)
535  if (fVerbose>2) {all[j].Print(); cout<<"\033[0;0m";}
536  }
537 
538  // does multiplicity match?
539  if (cnt_matches<f.nmin || cnt_matches>f.nmax) acc_evt = false;
540 
541  // is this a veto filter -> negate result
542  acc_evt = acc_evt^f.veto;
543 
544  if (fVerbose>2) cout <<"Filterset "<<ifs<<" Filter "<<i<<" : N_matched = "<<cnt_matches<<" : event "<<(!acc_evt?"not ":"")<<"accepted"<<endl<<endl<<endl;
545 
546  // global accept (of all filters)
547  acc_fset = (acc_fset && acc_evt);
548 
549  } // **** count filters
550 
551 
552  // -------------------
553  // Loop over mass filters
554  // -------------------
555  for (int i=0; i<(int)fFilterSets[ifs].size(); ++i)
556  {
557  // if the event cannot be accepted anymore, skip the next filter test
558  if (!acc_fset) continue;
559 
560  // event accept flag
561  bool acc_evt = true;
562 
563  PndSmpFilt &f = fFilterSets[ifs][i];
564 
565  // now only mass filters
566  if (!f.compo) continue;
567 
568  // ----------------
569  // do combinatorics
570  // ----------------
571 
572  // prepare lists of particles and the charged conjugation
573  PndSmpCandList *l[5] = {0}, *al[5] = {0};
574  std::vector<int> vpdg, vapdg;
575 
576  for (int j=0; j<f.ndau; ++j)
577  {
578  vpdg.push_back(f.pdg[j]);
579  vapdg.push_back(AntiPdgCode(f.pdg[j]));
580 
581  l[j] = &(pdgList[f.pdg[j]]);
582  al[j] = &(pdgList[AntiPdgCode(f.pdg[j])]);
583  }
584 
585  // *** do combinatorics
586  PndSmpCandList comblist = CombineList(0, l[0], l[1], l[2], l[3], l[4]);
587 
588  // do we want c.c. and is the cc'd list not the same as the original one (= a permutation)?
589  if (!f.nocc && !is_permutation(vpdg.begin(), vpdg.end(), vapdg.begin()))
590  {
591  PndSmpCandList anticomblist = CombineList(0, al[0], al[1], al[2], al[3], al[4]);
592  comblist.insert(comblist.end(), anticomblist.begin(), anticomblist.end());
593  }
594 
595  int cnt_matches = 0;
596 
597  // *** loop over composite particles
598  for (int j=0 ; j<(int)comblist.size() ; ++j)
599  {
600  TLorentzVector p4 = comblist[j].P4();
601 
602  // *** check mass window and kinematics of composite
603  bool acc_cand = (fabs(p4.M() - f.mcntr) < f.mwin/2.) && CheckKinematic(f, p4);
604 
605  // *** count track
606  if (acc_cand)
607  {
608  cnt_matches++;
609  if (fVerbose>2) cout << "\033[1;35m ** ";
610  }
611  else if (fVerbose>2) cout << " ";
612 
613  // *** (and print if verbose)
614  if (fVerbose>2) { comblist[j].Print(); cout<<"\033[0;0m";}
615  }
616 
617  // does multiplicity match?
618  if (cnt_matches<f.nmin || cnt_matches>f.nmax) acc_evt = false;
619 
620  // is this a veto filter -> negate result
621  acc_evt = acc_evt^f.veto;
622 
623  if (fVerbose>2) cout <<"Filterset "<<ifs<<" Filter "<<i<<" : N_matched = "<<cnt_matches<<" : event "<<(!acc_evt?"not ":"")<<"accepted"<<endl<<endl<<endl;
624 
625  // global accept (of all filters)
626  acc_fset = (acc_fset && acc_evt);
627 
628  } // **** mass filters
629 
630 
631  // the global event accept, being an OR connection of all filter sets ('event types' to be accepted)
632 
633  acc_glob = (acc_glob || acc_fset);
634  } // **** filter sets
635 
636 
637  //if (fVerbose>1) cout <<" --> EVENT "<<entry<<" "<<(!acc_glob?"NOT ":"")<<"ACCEPTED"<<endl<<endl<<endl;
638 
639  //if (acc_glob) {cnt_acc++;}
640  }
641 
642 
643  // Set the event number ALWAYS when filtering
645  fEvent->SetEventID(fEventNrFiltered);
646 
647  if ( !acc_glob ){
649  cout << "\n -E PndFilteredPrimaryGenerator: No event was found within " << iTry << " tries which satisfies your event filter.\n ";
650  cout << "I accept a random event as evtNr " << fEventNrFiltered << " to avoid infinite loops. \n";
651  cout << "Try increasing the max. number of tries or change your filter\n\n";
652  if (fVerbose > 3 ){
653  cout << iTry << " events simulated until I found a good one.\n";
654  cout << fEvtFilterStat.fGeneratedEvents << " events generated for finding " << fEventNr << " accepted events.\n";
655  cout << fEvtFilterStat.fFailedFilterEvents << " unsuccessful attempts in total to find an event that suits your filters\n\n";
656  }
657  }
658 
659  if (0 < fVerbose && active_filters && (fEventNrFiltered%fEventPrintFreq)==0) cout <<"[PndFilteredPrimaryGenerator] " << fEventNrFiltered << " / " << fEvtFilterStat.fGeneratedEvents << " generated events accepted.\n";
660 
661  return kTRUE;
662 }
663 // -------------------------------------------------------------------------
664 
MechFsc Print()
double pzmin
Definition: PndSmpFilt.h:36
std::vector< PndSmpCand > PndSmpCandList
int fVerbose
Definition: poormantracks.C:24
printf("RealTime=%f seconds, CpuTime=%f seconds\n", rtime, ctime)
Int_t res
Definition: anadigi.C:166
c4
Definition: plot_dirc.C:71
Int_t i
Definition: run_full.C:25
TTree * b
double phimin
Definition: PndSmpFilt.h:38
exit(0)
TH1F * nc
Definition: plot_eta_c.C:38
StrVec SplitString(TString s, TString delim=" ")
Splits a TString to substrings.
TLorentzVector s
Definition: Pnd2DStar.C:50
std::unordered_set< int > fSetFsPdg
set to identify particles from MC truth list which can be combined
c2
Definition: plot_dirc.C:39
TString cuts[MAX]
Definition: autocutx.C:35
double pzmax
Definition: PndSmpFilt.h:36
Simple container for filter definition (criteria) for PndFilteredPrimaryGenerator.
Definition: PndSmpFilt.h:19
PndFilteredPrimaryGenerator()
Default constructor.
double ptmax
Definition: PndSmpFilt.h:35
double pmin
Definition: PndSmpFilt.h:34
std::map< TString, int > fNameCodeMap
mapes names to (pdg) codes
bool CheckKinematic(const PndSmpFilt &f, const TLorentzVector &p4)
Checks whether P4 kinematics match the criteria of a PndSmpFilt.
for(int j=0;j< ncounts;j++)
Int_t fEventNrFiltered
Event number (Set by the filtered primary generator.
const int particle
bool nocc
Definition: PndSmpFilt.h:42
virtual Bool_t Init()
Initialize the event generator(s) and the event (veto) filter(s).
std::map< int, TString > fCodeNameMap
mapes (pdg) codes to names
Int_t a
Definition: anaLmdDigi.C:126
double pmax
Definition: PndSmpFilt.h:34
TDatabasePDG * fdbPdg
Shortcut to TDatabasePDG.
double mcntr
Definition: PndSmpFilt.h:41
std::vector< TString > fPartNames
particle names for particles to count (with and w/o charged specification, also simply tracks and neu...
Primary generator with added event filtering capabilities.
TFile * f
Definition: bump_analys.C:12
vector< PndSmpFilt > PndSmpFilterSet
void SetP4(TLorentzVector p4)
Sets LorentzVector.
Definition: PndSmpCand.h:49
friend F32vec4 fabs(const F32vec4 &a)
Definition: P4_F32vec4.h:47
c1
Definition: plot_dirc.C:35
double thtmax
Definition: PndSmpFilt.h:37
std::vector< TString > StrVec
TString name
c3
Definition: plot_dirc.C:50
double ptmin
Definition: PndSmpFilt.h:35
FairEvtFilterParams fEvtFilterStat
Contains the statistics of the event filtering process.
Bool_t Overlap(PndSmpCand *c)
Definition: PndSmpCand.h:70
virtual Bool_t GenerateEvent(FairGenericStack *pStack)
Calls event generators and the event filters.
void AddFilter(TString filterStr)
Registers a filter as a string to be parsed Each filter set consist of one filter definition or a num...
std::vector< PndSmpFilterSet > fFilterSets
Contains the filter-sets. Each filter set consist of one filter definition or a number of filters con...
fRun Init()
Definition: NHitsPerEvent.C:20
Int_t cnt
Definition: hist-t7.C:106
Int_t fEventPrintFreq
Print frequency for filtered events.
ClassImp(PndAnaContFact)
void PrintSmpCandList(PndSmpCandList l, TString name="")
Prints a candidate lits.
TString name
Definition: PndSmpFilt.h:27
void GetRangeInt(TString s, int &a, int &b, TString delim="..")
Turns a string of the form &lt;int&gt;&lt;delim&gt;&lt;int&gt; (e.g. &quot;3..8&quot;) to a range a,b.
PndSmpCandList CombineList(int pdg, PndSmpCandList *l0, PndSmpCandList *l1, PndSmpCandList *l2=0, PndSmpCandList *l3=0, PndSmpCandList *l4=0)
Combines upt to five particle lists of PndSmpCand with overlap and double counting prevention...
if(fWindowIsBox)
double mwin
Definition: PndSmpFilt.h:41
bool compo
Definition: PndSmpFilt.h:29
int pdg[5]
Definition: PndSmpFilt.h:32
double phimax
Definition: PndSmpFilt.h:38
Int_t fVerbose
Level of commenting output, 0 means no output, higher gives more output.
bool veto
Definition: PndSmpFilt.h:30
std::vector< int > fNamePdg
particle codes for particles to count (with and w/o charged specification, also simply tracks and neu...
int AntiPdgCode(int pdg)
Gets anti-pdg code, if exists. If not returns the code itself (particle is its anti-particle) ...
double thtmin
Definition: PndSmpFilt.h:37
std::vector< int > fCombFsPdg
particle codes for the lists used for combinatorics; !!! the codes are not selected from MC truth...
void GetRangeDouble(TString s, double &a, double &b, TString delim=",", bool forceset=false)
Turns a string of the form &lt;float&gt;&lt;delim&gt;&lt;float&gt; (e.g. &quot;124.2,178.3&quot;) to a range a,b.
Simple particle candidate to perform simple combinatorics and particle counting for event filtering...
Definition: PndSmpCand.h:23