ATLAS Offline Software
scenario_dijet.py
Go to the documentation of this file.
1 # Copyright (C) 2002-2023 CERN for the benefit of the ATLAS collaboration
2 
3 from TrigHLTJetHypo.RepeatedConditionParams import RepeatedConditionParams
4 from TrigHLTJetHypo.HelperConfigToolParams import HelperConfigToolParams
5 from TrigHLTJetHypo.ConditionDefaults import defaults
6 from TrigHLTJetHypo.make_treevec import make_treevec
7 
8 import re
9 
10 pattern_thresh_pt = r'^DIJET'\
11  r'((?P<j12ptlo>\d*)j12pt(?P<j12pthi>\d*)XX|'\
12  r'(?P<j1ptlo>\d*)j1pt(?P<j1pthi>\d*)XX'\
13  r'(?P<j2ptlo>\d*)j2pt(?P<j2pthi>\d*)XX)'
14 
15 
16 pattern_thresh_et = r'^DIJET'\
17  r'((?P<j12etlo>\d*)j12et(?P<j12ethi>\d*)XX|'\
18  r'(?P<j1etlo>\d*)j1et(?P<j1ethi>\d*)XX'\
19  r'(?P<j2etlo>\d*)j2et(?P<j2ethi>\d*)XX)'
20 
21 
22 pattern_common = r'((?P<j12etalo>\d*)j12eta(?P<j12etahi>\d*)XX|'\
23  r'((?P<j1etalo>\d*)j1eta(?P<j1etahi>\d*)XX)?'\
24  r'((?P<j2etalo>\d*)j2eta(?P<j2etahi>\d*)XX)?)?'\
25  r'(?P<djmasslo>\d*)djmass(?P<djmasshi>\d*)'\
26  r'(XX(?P<djdphilo>\d*)djdphi(?P<djdphihi>\d*))?'\
27  r'(XX(?P<djdetalo>\d*)djdeta(?P<djdetahi>\d*))?$'
28 
29 
30 pattern_pt = pattern_thresh_pt + pattern_common
31 rgx_pt = re.compile(pattern_pt)
32 
33 pattern_et = pattern_thresh_et + pattern_common
34 rgx_et = re.compile(pattern_et)
35 
36 
37 def get_dijet_args_from_matchdict(groupdict, keystubs):
38 
39  # find the constructor arguments for each keys starting
40  # with the elements of the ksystubs list
41 
42  condargs = []
43 
44  dj_keystubs = set([k[:-2] for k in groupdict if k.startswith('dj')])
45 
46  for k in dj_keystubs:
47  vals = defaults(k, groupdict[k+'lo'], groupdict[k+'hi'])
48  condargs.append((k, vals))
49 
50  return condargs
51 
52 
53 def get_singlejet_args_from_matchdict(groupdict, threshold_var, jstr):
54  """obtain the single jet cuts."""
55 
56  assert jstr in ('j1','j2')
57  assert threshold_var in ('pt', 'et')
58 
59  condargs = []
60 
61  vals = defaults(threshold_var,
62  groupdict[jstr+threshold_var+'lo'],
63  groupdict[jstr+threshold_var+'hi'])
64 
65  condargs.append((threshold_var, vals))
66 
67  vals = defaults('eta', groupdict[jstr+'etalo'], groupdict[jstr+'etahi'],)
68  condargs.append(('eta', vals))
69 
70  return condargs
71 
72 
73 def scenario_dijet(scenario, chainPartInd):
74  """ original dijet scenario work by J. Bossio.
75 
76  produce a singe element list containing a HelperToolConfigTool.
77 
78  Decodes the dijet scenario to form aConditions to select jet pairs
79  with Conditions on the jet pair, and each of the two jets separately.
80 
81  Currently supported cuts:
82  - dijet mass
83  - dijet phi
84  - dijet eta
85  - jet1 et, eta
86  - jet2 et, eta
87 
88  - default values are used for unspecified cuts, except for delta phi and
89  delta eta for which no cut is applied if not requested
90  The cut set can be extended according to the pattern
91 
92 
93  example scenarios:
94  DIJET50j1etXX80j2etXX0j1eta240XX0j2eta320XX700djmass
95  mixed j1/j2 et/eta values
96 
97  DIJET80j12etXX0j12eta240XX700djmass
98  same et/eta cuts for j1 and j2
99 
100  DIJET80j12etXX700djmassXX26djdphi
101  including delta phi cut
102 
103  DIJET70j12etXX1000djmassXX20djdphiXX40djdeta
104  including delta eta cut
105 
106  The tree vector is [0, 0, 1, 1]
107  # pos 0: root; pos 1 dijet cuts; pos 2: j1 cuts; pos 3: j2 cuts'"""
108 
109  assert scenario.startswith('DIJET'), \
110  'routing error, module %s: bad scenario %s' % (__name__, scenario)
111 
112  # Note:
113  # j12et and j12eta respectively use the same values for j1et/j2et
114  # and j1eta/j2eta
115  # j1eta/j2eta,j12eta is allowed not to be in the scenario,
116  # default values will be used in such a case: 0eta490
117  # djdphi/djdeta is allowed not to be in the scenario,
118  # no djdphi/djdeta cut will be applied in such a case
119 
120 
121  threshold_var = 'pt'
122  m = rgx_pt.match(scenario)
123 
124  if m is None:
125  threshold_var = 'et'
126  m = rgx_et.match(scenario)
127 
128  assert m is not None, \
129  'scenario_dijet.py - regex pat %s or %s do not match scenario %s' % (
130  pattern_pt, pattern_et, scenario)
131 
132  groupdict = m.groupdict()
133 
134  to_delete = [k for k in groupdict if groupdict[k] is None]
135  for k in to_delete: del groupdict[k]
136 
137  def massage_thresh(threshold_var, gdict):
138  to_delete = []
139  for k in ('j12'+threshold_var+'lo',
140  'j12'+threshold_var+'hi',
141  'j12etalo',
142  'j12etahi'):
143  if k in gdict:
144  to_delete.append(k)
145  new_key = 'j1' + k[len('j12'):]
146  gdict[new_key] = gdict[k]
147  new_key = 'j2' + k[len('j12'):]
148  gdict[new_key] = gdict[k]
149 
150  for k in to_delete:
151  del gdict[k]
152 
153  return gdict
154 
155  groupdict = massage_thresh(threshold_var, groupdict)
156 
157  # always make an eta cut even if not in scenario
158  if 'j1etalo' not in groupdict: groupdict['j1etalo'] = '0'
159  if 'j1etahi' not in groupdict: groupdict['j1etahi'] = '490'
160  if 'j2etalo' not in groupdict: groupdict['j2etalo'] = '0'
161  if 'j2etahi' not in groupdict: groupdict['j2etahi'] = '490'
162 
163 
164  # get the Condition parameters (cut values) for the dijet Conditions
165  keystubs = set([k[:-2] for k in groupdict if k.startswith('dj')])
166  condargs = get_dijet_args_from_matchdict(groupdict, keystubs)
167 
168  # treeVec is [0, 0, 1, 1] handle non-root nodes here
169 
170  repcondargs = [RepeatedConditionParams(tree_id = 1,
171  tree_pid=0,
172  chainPartInd=-1,
173  condargs=condargs)]
174 
175 
176  # make the condargs and the containing rep condition for j1
177 
178  condargs1 = get_singlejet_args_from_matchdict(groupdict,
179  threshold_var,
180  'j1')
181 
182  condargs2 = get_singlejet_args_from_matchdict(groupdict,
183  threshold_var,
184  'j2')
185 
186 
187  twins = condargs1 == condargs2
188  if twins:
189  repcondargs.append(RepeatedConditionParams(tree_id = 2,
190  tree_pid=1,
191  multiplicity=2,
192  chainPartInd=chainPartInd,
193  condargs=condargs1))
194  else:
195 
196  repcondargs.append(RepeatedConditionParams(tree_id = 2,
197  tree_pid=1,
198  chainPartInd=chainPartInd,
199  condargs=condargs1))
200 
201  repcondargs.append(RepeatedConditionParams(tree_id = 3,
202  tree_pid=1,
203  chainPartInd=chainPartInd,
204  condargs=condargs1))
205 
206 
207 
208  # make pass through filter params for each condition in the tree.
209  nconds = len(repcondargs)
210  filterparams = []
211  filterparam_inds = [-1 for i in range(nconds)]
212 
213 
214  # parameters to initalise the AlgTool that initialises the helper AlgTool
215 
216  # treevec[i] gives the tree_id of the parent of the
217  # node with tree_id = i
218  treevec = make_treevec(repcondargs)
219  if twins:
220  assert treevec == [0, 0, 1]
221  else:
222  assert treevec == [0, 0, 1, 1]
223 
224  assert len(repcondargs) == len(filterparam_inds)
225 
226  helper_params = HelperConfigToolParams(treevec=treevec,
227  repcondargs=repcondargs,
228  filterparams=filterparams,
229  filterparam_inds=filterparam_inds)
230 
231  return [helper_params] # a list is one entry per FastReduction tree
232 
233 
234 
python.scenario_dijet.scenario_dijet
def scenario_dijet(scenario, chainPartInd)
Definition: scenario_dijet.py:73
plotBeamSpotVxVal.range
range
Definition: plotBeamSpotVxVal.py:195
CxxUtils::set
constexpr std::enable_if_t< is_bitmask_v< E >, E & > set(E &lhs, E rhs)
Convenience function to set bits in a class enum bitmask.
Definition: bitmask.h:224
python.scenario_dijet.get_dijet_args_from_matchdict
def get_dijet_args_from_matchdict(groupdict, keystubs)
Definition: scenario_dijet.py:37
python.scenario_dijet.get_singlejet_args_from_matchdict
def get_singlejet_args_from_matchdict(groupdict, threshold_var, jstr)
Definition: scenario_dijet.py:53
Base_Fragment.defaults
dictionary defaults
This includes now the top quark, the leptons and the bosons.
Definition: GeneratorFilters/share/common/Base_Fragment.py:79
python.make_treevec.make_treevec
def make_treevec(repcondargs)
Definition: make_treevec.py:3