Skip to content

Commit

Permalink
Make selections configurable from options json
Browse files Browse the repository at this point in the history
  • Loading branch information
sam-may committed Feb 4, 2021
1 parent 2b96e7e commit 8af3574
Show file tree
Hide file tree
Showing 6 changed files with 84 additions and 46 deletions.
33 changes: 32 additions & 1 deletion Preselection/data/HH_ggTauTau_default.json
Original file line number Diff line number Diff line change
Expand Up @@ -14,5 +14,36 @@
"muon1_pt", "muon1_eta", "muon2_pt", "muon2_eta",
"tau1_pt", "tau1_eta", "tau2_pt", "tau2_eta", "tau1_id_vs_e", "tau1_id_vs_m", "tau1_id_vs_j", "tau2_id_vs_e", "tau2_id_vs_m", "tau2_id_vs_j",
"n_tau", "n_electrons", "n_muons"
]
],
"selection_options" : {
"photons" : {
"idmva_cut" : -0.7
},
"electrons" : {
"pt" : 10.0,
"eta" : 2.4,
"ip_xy" : 0.045,
"ip_z" : 0.2,
"dR_pho" : 0.2
},
"muons" : {
"pt" : 10.0,
"eta" : 2.4,
"ip_xy" : 0.045,
"ip_z" : 0.2,
"rel_iso" : 0.3,
"dR_pho" : 0.2
},
"taus" : {
"pt" : 20.0,
"eta" : 2.3,
"dz" : 0.2,
"DeepTau_vs_e" : 2,
"DeepTau_vs_mu" : 1,
"DeepTau_vs_jet" : 8,
"dR_pho" : 0.2,
"dR_lep" : 0.2
},
"n_leptons_and_taus" : 1
}
}
22 changes: 13 additions & 9 deletions Preselection/helpers/loop_helper.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@
import awkward
import multiprocessing
import time
import copy

import selections.photon_selections as photon_selections
import selections.analysis_selections as analysis_selections
Expand Down Expand Up @@ -217,19 +218,22 @@ def write_summary(self):

def select_events(self, events, metadata):
# Dipho preselection
events = photon_selections.diphoton_preselection(events, metadata["resonant"], self.debug)
events.Photon = events.Photon[photon_selections.select_photons(events, self.debug)]
options = copy.deepcopy(self.selection_options)
for key, value in metadata.items(): # add sample-specific options to selection options
options[key] = value
events = photon_selections.diphoton_preselection(events, options, self.debug)
events.Photon = events.Photon[photon_selections.select_photons(events, options, self.debug)]

if self.selections == "HHggTauTau_InclusivePresel":
events = analysis_selections.ggTauTau_inclusive_preselection(events, self.debug)
events.Electron = events.Electron[lepton_selections.select_electrons(events, events.Photon, self.debug)]
events.Muon = events.Muon[lepton_selections.select_muons(events, events.Photon, self.debug)]
events.Tau = events.Tau[tau_selections.select_taus(events, events.Photon, events.Muon, events.Electron, self.debug)]
events = analysis_selections.ggTauTau_inclusive_preselection(events, options, self.debug)
events.Electron = events.Electron[lepton_selections.select_electrons(events, events.Photon, options, self.debug)]
events.Muon = events.Muon[lepton_selections.select_muons(events, events.Photon, options, self.debug)]
events.Tau = events.Tau[tau_selections.select_taus(events, events.Photon, events.Muon, events.Electron, options, self.debug)]

elif self.selections == "ttH_LeptonicPresel":
events = analysis_selections.tth_leptonic_preselection(events, self.debug)
events.Electron = events.Electron[lepton_selections.select_electrons(events, events.Photon, self.debug)]
events.Muon = events.Muon[lepton_selections.select_muons(events, events.Photon, self.debug)]
events = analysis_selections.tth_leptonic_preselection(events, options, self.debug)
events.Electron = events.Electron[lepton_selections.select_electrons(events, events.Photon, options, self.debug)]
events.Muon = events.Muon[lepton_selections.select_muons(events, events.Photon, options, self.debug)]

return events

Expand Down
16 changes: 8 additions & 8 deletions Preselection/selections/analysis_selections.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,28 +8,28 @@
import selections.tau_selections as tau_selections
import selections.photon_selections as photon_selections

def ggTauTau_inclusive_preselection(events, debug):
def ggTauTau_inclusive_preselection(events, options, debug):
cut_diagnostics = utils.CutDiagnostics(events = events, debug = debug, cut_set = "[analysis_selections.py : ggTauTau_inclusive_preselection]")

# Get number of electrons, muons, taus
electron_selection = lepton_selections.select_electrons(events, events.Photon, debug)
muon_selection = lepton_selections.select_muons(events, events.Photon, debug)
tau_selection = tau_selections.select_taus(events, events.Photon, events.Muon[muon_selection], events.Electron[electron_selection], debug)
electron_selection = lepton_selections.select_electrons(events, events.Photon, options, debug)
muon_selection = lepton_selections.select_muons(events, events.Photon, options, debug)
tau_selection = tau_selections.select_taus(events, events.Photon, events.Muon[muon_selection], events.Electron[electron_selection], options, debug)

n_electrons = awkward.num(events.Electron[electron_selection])
n_muons = awkward.num(events.Muon[muon_selection])
n_taus = awkward.num(events.Tau[tau_selection])

# Require >= 1 lep/tau
n_leptons_and_taus = n_electrons + n_muons + n_taus
lep_tau_cut = n_leptons_and_taus >= 1
lep_tau_cut = n_leptons_and_taus >= options["n_leptons_and_taus"]

# Require OS leptons/taus for events with 2 leptons/taus
sum_charge = awkward.sum(events.Electron[electron_selection].charge, axis=1) + awkward.sum(events.Muon[muon_selection].charge, axis=1) + awkward.sum(events.Tau[tau_selection].charge, axis=1)
charge_cut = sum_charge == 0
n_lep_cut = n_leptons_and_taus == 2
two_leptons = n_leptons_and_taus == 2
not_two_leptons = n_leptons_and_taus != 2
os_cut = (n_lep_cut & charge_cut) | not_two_leptons # only require 2 OS leptons if there are ==2 leptons in the event
os_cut = (two_leptons & charge_cut) | not_two_leptons # only require 2 OS leptons if there are ==2 leptons in the event

all_cuts = lep_tau_cut & os_cut
cut_diagnostics.add_cuts([lep_tau_cut, os_cut, all_cuts], ["N_leptons + N_taus >= 1", "OS dileptons", "all"])
Expand All @@ -38,7 +38,7 @@ def ggTauTau_inclusive_preselection(events, debug):

return events

def tth_leptonic_preselection(events, debug):
def tth_leptonic_preselection(events, options, debug):
cut_diagnostics = utils.CutDiagnostics(events = events, debug = debug, cut_set = "[analysis_selections.py : tth_leptonic_preselection]")

# Get number of electrons, muons
Expand Down
28 changes: 15 additions & 13 deletions Preselection/selections/lepton_selections.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,31 +7,33 @@

DR_LEP_PHO = 0.2

def select_electrons(events, photons, debug):
def select_electrons(events, photons, options, debug):
cut_diagnostics = utils.ObjectCutDiagnostics(objects = events.Electron, cut_set = "[lepton_selections.py : select_electrons]", debug = debug)

pt_cut = events.Electron.pt > 10
eta_cut = abs(events.Electron.eta) < 2.5
ip_xy_cut = abs(events.Electron.dxy) < 0.045
ip_z_cut = abs(events.Electron.dz) < 0.2
pt_cut = events.Electron.pt > options["electrons"]["pt"]
eta_cut = abs(events.Electron.eta) < options["electrons"]["eta"]
ip_xy_cut = abs(events.Electron.dxy) < options["electrons"]["ip_xy"]
ip_z_cut = abs(events.Electron.dz) < options["electrons"]["ip_z"]
id_cut = (events.Electron.mvaFall17V2Iso_WP90 == True | ((events.Electron.mvaFall17V2noIso_WP90 == True) & (events.Electron.pfRelIso03_all < 0.3)))
dR_cut = object_selections.select_deltaR(events, events.Electron, photons, DR_LEP_PHO, debug)
# TODO: make ID cut configurable
# also: ID cut has pretty low efficiency on signal, loosen?
dR_cut = object_selections.select_deltaR(events, events.Electron, photons, options["electrons"]["dR_pho"], debug)

electron_cut = pt_cut & eta_cut & ip_xy_cut & ip_z_cut & id_cut & dR_cut

cut_diagnostics.add_cuts([pt_cut, eta_cut, ip_xy_cut, ip_z_cut, id_cut, dR_cut, electron_cut], ["pt", "eta", "ip_xy", "ip_z", "id", "dR", "all"])

return electron_cut

def select_muons(events, photons, debug):
def select_muons(events, photons, options, debug):
cut_diagnostics = utils.ObjectCutDiagnostics(objects = events.Muon, cut_set = "[lepton_selections.py : select_muons]", debug = debug)

pt_cut = events.Muon.pt > 10
eta_cut = abs(events.Muon.eta) < 2.4
ip_xy_cut = abs(events.Muon.dxy) < 0.045
ip_z_cut = abs(events.Muon.dz) < 0.2
iso_cut = events.Muon.pfRelIso03_all < 0.3
dR_cut = object_selections.select_deltaR(events, events.Muon, photons, DR_LEP_PHO, debug)
pt_cut = events.Muon.pt > options["muons"]["pt"]
eta_cut = abs(events.Muon.eta) < options["muons"]["eta"]
ip_xy_cut = abs(events.Muon.dxy) < options["muons"]["ip_xy"]
ip_z_cut = abs(events.Muon.dz) < options["muons"]["ip_z"]
iso_cut = events.Muon.pfRelIso03_all < options["muons"]["rel_iso"]
dR_cut = object_selections.select_deltaR(events, events.Muon, photons, options["muons"]["dR_pho"], debug)

muon_cut = pt_cut & eta_cut & ip_xy_cut & ip_z_cut & iso_cut & dR_cut

Expand Down
11 changes: 6 additions & 5 deletions Preselection/selections/photon_selections.py
Original file line number Diff line number Diff line change
Expand Up @@ -18,13 +18,14 @@
2. Trim objects with object-level selections afterwards
"""

def diphoton_preselection(events, resonant, debug):
def diphoton_preselection(events, options, debug):
# Initialize cut diagnostics tool for debugging
cut_diagnostics = utils.CutDiagnostics(events = events, debug = debug, cut_set = "[photon_selections.py : diphoton_preselection]")

photons = events.Photon[select_photons(events, debug)]
photons = events.Photon[select_photons(events, options, debug)]

### mgg cut ###
resonant = options["resonant"]
if resonant:
mgg_mask = numpy.array(events.ggMass > 100) & numpy.array(events.ggMass < 180)
else:
Expand All @@ -41,7 +42,7 @@ def diphoton_preselection(events, resonant, debug):
pt_mgg_cut = lead_pt_mgg_cut & sublead_pt_mgg_cut

### pho ID MVA cuts ###
pho_idmva_requirement = photons.mvaID > -0.7
pho_idmva_requirement = photons.mvaID > options["photons"]["idmva_cut"]
pho_idmva_cut = awkward.num(photons[pho_idmva_requirement]) >= 2 # both photons must pass id mva requirement

### electron veto cut ###
Expand All @@ -58,13 +59,13 @@ def diphoton_preselection(events, resonant, debug):

return events

def select_photons(events, debug):
def select_photons(events, options, debug):
cut_diagnostics = utils.ObjectCutDiagnostics(objects = events.Photon, cut_set = "[photon_selections.py : select_photons]", debug = debug)

pt_cut = events.Photon.pt > 25
eta_cut = abs(events.Photon.eta) < 2.5
pt_mgg_cut = (events.Photon.pt / events.ggMass) >= 0.25
idmva_cut = events.Photon.mvaID > -0.7
idmva_cut = events.Photon.mvaID > options["photons"]["idmva_cut"]
eveto_cut = events.Photon.electronVeto == 1
photon_cut = pt_cut & eta_cut & pt_mgg_cut & idmva_cut & eveto_cut

Expand Down
20 changes: 10 additions & 10 deletions Preselection/selections/tau_selections.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,21 +8,21 @@
DR_TAU_PHO = 0.2
DR_TAU_LEP = 0.2

def select_taus(events, photons, muons, electrons, debug):
def select_taus(events, photons, muons, electrons, options, debug):
cut_diagnostics = utils.ObjectCutDiagnostics(objects = events.Tau, cut_set = "[tau_selections.py : select_taus]", debug = debug)

pt_cut = events.Tau.pt > 20
eta_cut = abs(events.Tau.eta) < 2.3
pt_cut = events.Tau.pt > options["taus"]["pt"]
eta_cut = abs(events.Tau.eta) < options["taus"]["eta"]
decay_mode_cut = events.Tau.idDecayModeNewDMs == True
dz_cut = abs(events.Tau.dz) < 0.2
dz_cut = abs(events.Tau.dz) < options["taus"]["dz"]

id_electron_cut = events.Tau.idDeepTau2017v2p1VSe >= 2
id_muon_cut = events.Tau.idDeepTau2017v2p1VSmu >= 1
id_jet_cut = events.Tau.idDeepTau2017v2p1VSjet >= 8
id_electron_cut = events.Tau.idDeepTau2017v2p1VSe >= options["taus"]["DeepTau_vs_e"]
id_muon_cut = events.Tau.idDeepTau2017v2p1VSmu >= options["taus"]["DeepTau_vs_mu"]
id_jet_cut = events.Tau.idDeepTau2017v2p1VSjet >= options["taus"]["DeepTau_vs_jet"]

dR_pho_cut = object_selections.select_deltaR(events, events.Tau, photons, DR_TAU_PHO, debug)
dR_muon_cut = object_selections.select_deltaR(events, events.Tau, muons, DR_TAU_LEP, debug)
dR_ele_cut = object_selections.select_deltaR(events, events.Tau, electrons, DR_TAU_LEP, debug)
dR_pho_cut = object_selections.select_deltaR(events, events.Tau, photons, options["taus"]["dR_pho"], debug)
dR_muon_cut = object_selections.select_deltaR(events, events.Tau, muons, options["taus"]["dR_lep"], debug)
dR_ele_cut = object_selections.select_deltaR(events, events.Tau, electrons, options["taus"]["dR_lep"], debug)

tau_cut = pt_cut & eta_cut & decay_mode_cut & dz_cut & id_electron_cut & id_muon_cut & id_jet_cut & dR_pho_cut & dR_muon_cut & dR_ele_cut

Expand Down

0 comments on commit 8af3574

Please sign in to comment.