def getCrossSection(analysis,channel,period,**kwargs): doDataDriven = kwargs.pop('doDataDriven',False) cut = kwargs.pop('cut','1') scaleFactor = kwargs.pop('scaleFactor','event.gen_weight*event.pu_weight*event.lep_scale*event.trig_scale') directory = kwargs.pop('directory','') ntuples = 'ntuples/%s_%iTeV_%s' % (analysis,period,channel) saves = '%s_%s_%iTeV' % (analysis,channel,period) mergeDict = getMergeDict(period) numleps = { 'Hpp2l': 2, 'Z' : 2, 'TT' : 2, 'WZ' : 3, 'WZ_W' : 1, 'WZ_Dijet': 1, 'Hpp3l': 3, 'Hpp4l': 4, } nl = numleps[analysis] finalStates, leptons = getChannels(nl) if analysis in ['WZ']: finalStates = ['eee','eem','mme','mmm'] sigMap = getSigMap(nl) channelBackground = getChannelBackgrounds(period) plotter = Plotter(channel,ntupleDir=ntuples,saveDir=saves,period=period,mergeDict=mergeDict,dataDriven=doDataDriven) plotter.initializeBackgroundSamples([sigMap[period][x] for x in channelBackground[channel]]) plotter.initializeDataSamples([sigMap[period]['data']]) intLumi = getIntLumiMap()[period] plotter.setIntLumi(intLumi) # get acceptance and efficiency numbers # just WZ # zWindow, fiducial # 4 channels accEff = getAcceptanceEfficiency(analysis)
def gen_card(self, file_name, **kwargs): doDataDriven = kwargs.pop("doDataDriven", True) # get the plotter nl = 3 sigMap = getSigMap(nl) intLumiMap = getIntLumiMap() mergeDict = getMergeDict(self.period) channelBackground = getChannelBackgrounds(self.period) channels, leptons = getChannels(nl) saves = "%s_%s_%iTeV" % (self.analysis, self.region, self.period) plotter = Plotter( self.region, ntupleDir=self.ntuple_dir, saveDir=saves, period=self.period, rootName="plots_limits_wz", mergeDict=mergeDict, scaleFactor=self.scalefactor, datadriven=True, ) plotter.initializeBackgroundSamples( [sigMap[self.period][x] for x in channelBackground[self.region + "datadriven"]] ) plotter.initializeDataSamples([sigMap[self.period]["data"]]) plotter.setIntLumi(intLumiMap[self.period]) # set expected and observed yields sources = ( [ x for x in channelBackground[self.region + "datadriven"] if x not in ["TT", "T", "DY", "Z", "Zfiltered", "WW"] ] + ["datadriven"] if doDataDriven else channelBackground[self.region] ) for bg in sources: self.log.info("Processing {0}".format(bg)) val, err = plotter.getNumEntries(self.selection, sigMap[self.period][bg], doError=True) statname = "stat_{0}_{1}".format(bg, file_name.split(".")[0]) staterrs = {bg: err / val + 1.0 if val else 1.0} if self.doStat: self.add_systematics(statname, "lnN", **staterrs) if bg in ["WZ"]: self.datacard.add_sig(bg, val) else: self.datacard.add_bkg(bg, val) self.log.info("Processing observed") self.datacard.set_observed(plotter.getDataEntries(self.selection)) # write out the datacard self.log.info("Saving card to file") with open("%s/%s" % (self.out_dir, file_name), "w") as outfile: outfile.write(self.datacard.dump())
def getPlotter(self,analysis,region,runPeriod,mass,runTau,plotName,doFakes): nl = 3 if analysis=='Hpp3l' or analysis=='WZ' else 4 ntuples = getNtupleDirectory(analysis,region,runPeriod) saves = '%s_%s_%iTeV' % (analysis,region,runPeriod) sigMap = getSigMap(nl,mass) intLumiMap = getIntLumiMap() mergeDict = getMergeDict(runPeriod) regionBackground = getChannelBackgrounds(runPeriod) channels, leptons = getChannels(nl,runTau=runTau) plotter = Plotter(region,ntupleDir=ntuples,saveDir=saves,period=runPeriod,rootName=plotName,mergeDict=mergeDict,scaleFactor=self.scalefactor) if not doFakes: plotter.initializeBackgroundSamples([sigMap[runPeriod][x] for x in regionBackground[analysis]]) if runPeriod==8: plotter.initializeDataSamples([sigMap[runPeriod]['data']]) plotter.setIntLumi(intLumiMap[runPeriod]) return plotter
def calculateLeptonSystematic(mass,chanCuts,chanScales,**kwargs): do4l = kwargs.pop('do4l',False) analysis = 'Hpp3l' region = 'Hpp3l' runPeriod = 8 nl = 3 ntuples = getNtupleDirectory(analysis,region,runPeriod) saves = '%s_%s_%sTeV' % (analysis,region,runPeriod) sigMap = getSigMap(4,mass) if do4l else getSigMap(nl,mass) intLumiMap = getIntLumiMap() mergeDict = getMergeDict(runPeriod) regionBackground = { 'Hpp3l' : ['T','TT', 'TTV','W','Z','VVV','WW','ZZ','WZ'], 'Hpp4l' : ['TT','Z','DB'] } channels, leptons = getChannels(nl) plotter = Plotter(analysis,ntupleDir=ntuples,saveDir=saves,period=runPeriod,rootName='systematics',mergeDict=mergeDict) plotter.initializeBackgroundSamples([sigMap[runPeriod][x] for x in regionBackground[analysis]]) plotter.initializeSignalSamples([sigMap[runPeriod]['Sig']]) plotter.initializeDataSamples([sigMap[runPeriod]['data']]) plotter.setIntLumi(intLumiMap[runPeriod]) fullCut = 'finalstate.mass>100 && finalstate.sT>1.1*%f+60. && fabs(z1.mass-%f)>80. && h1.dPhi<%f/600.+1.95' %(mass,ZMASS,mass) finalSRCut = 'h1.mass>0.9*%f && h1.mass<1.1*%f' %(mass,mass) totBG = 0 totBG_scaled = 0 for c,s in zip(chanCuts,chanScales): chanBG = s*plotter.getNumEntries('%s && %s && %s' %(c,fullCut,finalSRCut),plotter.signal[0],scaleup=False) chanBG_scaled = s*plotter.getNumEntries('%s && %s && %s' %(c,fullCut,finalSRCut),plotter.signal[0],scaleup=True) totBG += chanBG totBG_scaled += chanBG_scaled sigSelSys = (totBG_scaled-totBG)/totBG return sigSelSys+1
#cut = 'z1.PassTight1 && z1.PassTight2 && w1.PassTight1 && finalstate.mass>100. && (z1.Pt1>20.&&z1.Pt2>10.) && fabs(z1.mass-%f) < 20 && w1.mll_z1_1>4 && w1.mll_z1_2>4 && w1.Pt1>20. && finalstate.met>30.' % ZMASS #cut = 'z1.PassTight1 && z1.PassTight2 && w1.PassTight1 && finalstate.mass>100. && (z1.Pt1>20.&&z1.Pt2>10.) && fabs(z1.mass-%f) < 25 && w1.mll_z1_1>4 && w1.mll_z1_2>4 && w1.Pt1>20. && finalstate.met>30.' % ZMASS #cut = 'z1.PassTight1 && z1.PassTight2 && w1.PassTight1 && finalstate.mass>100. && (z1.Pt1>20.&&z1.Pt2>10.) && fabs(z1.mass-%f) < 30 && w1.mll_z1_1>4 && w1.mll_z1_2>4 && w1.Pt1>20. && finalstate.met>30.' % ZMASS ntuples = 'ntuples/%s_%iTeV_%s' % (analysis,period,channel) saves = '%s_%s_%iTeV' % (analysis,channel,period) mergeDict = getMergeDict(period) nl = 3 finalStates, leptons = getChannels(nl) finalStates = ['eee','eem','mme','mmm'] s = 'WZ' sigMap = getSigMap(nl) channelBackground = getChannelBackgrounds(period) plotter = Plotter(channel,ntupleDir=ntuples,saveDir=saves,period=period,mergeDict=mergeDict,datadriven=False,rootName='wz_yields') plotter.initializeBackgroundSamples([sigMap[period][x] for x in channelBackground[channel+'datadriven']]) plotter.initializeDataSamples([sigMap[period]['data']]) intLumi = getIntLumiMap()[period] plotter.setIntLumi(intLumi) dataDrivenMC = channelBackground[channel+'datadriven'] + ['datadriven'] allMC = channelBackground[channel] + ['ZG','Z'] ##################### ### Get FakeRates ### ##################### if doFakes: logger.info('Load fake rates') fakesFile = 'InitialStateAnalysis/Analyzers/python/scale_factors/fakes_trigIso_dijet_13TeV.json' fakerates = {} with open(fakesFile,'r') as f: fakerates = json.load(f)
def generate(analysis, channel, period, **kwargs): ''' Generate root files Files are of the form: AnalysisChannel Channel0 Variable0 sample0 sample1 ... data Variable1 ... ''' logger = logging.getLogger(__name__) cut = kwargs.pop('cut','1') scaleFactor = kwargs.pop('scaleFactor','event.gen_weight*event.pu_weight*event.lep_scale*event.trig_scale') force = kwargs.pop('force','False') if force: logger.info('%s:%s:%iTeV: Forcing reprocessing' % (analysis, channel, period)) # get hashes cut, cuthash = hashcut(cut) scaleFactor, scalefactorhash = hashscalefactor(scaleFactor) logger.info('%s:%s:%iTeV: Running with selection %s' % (analysis, channel, period, cut)) rootPath = 'rootfiles/%s_%s_%iTeV/%s/%s' % (analysis,channel, period,cuthash,scalefactorhash) python_mkdir(rootPath) selectionDict = { # name : (variable, binning, selection), 'sT' : (['finalstate.sT'], [40,0,1000], cut), 'numJets30' : (['finalstate.jetVeto30'], [8,0,8], cut), 'elecVetoLoose' : (['finalstate.elecVetoLoose'], [8,0,8], cut), 'muonVetoLoose' : (['finalstate.muonVetoLoose'], [8,0,8], cut), 'elecVetoTight' : (['finalstate.elecVetoTight'], [8,0,8], cut), 'muonVetoTight' : (['finalstate.muonVetoTight'], [8,0,8], cut), 'bjetVeto30Medium' : (['finalstate.bjetVeto30Medium'], [8,0,8], cut), 'met' : (['finalstate.met'], [40,0,200], cut), 'mass' : (['finalstate.mass'], [40,0,400], cut), 'puVertices' : (['event.nvtx'], [50,0,50], cut), } if analysis in ['Hpp3l','Hpp4l'] or region in ['Hpp2l']: selectionDict['hppMass'] = (['h1.mass'], [24,0,600], cut) selectionDict['hppDPhi'] = (['h1.dPhi'], [32,0,3.2], cut) selectionDict['hppPt'] = (['h1.Pt'], [40,0,400], cut) selectionDict['hppPt1'] = (['h1.Pt1'], [40,0,200], cut) selectionDict['hppPt2'] = (['h1.Pt2'], [40,0,200], cut) selectionDict['hppIso1'] = (['h1.Iso1'], [50,0,0.5], cut) selectionDict['hppIso2'] = (['h1.Iso2'], [50,0,0.5], cut) selectionDict['hppDR'] = (['h1.dR'], [60,0,6], cut) if analysis in ['Z', 'Hpp3l', 'Hpp4l', 'WZ'] or region in ['Z', 'TT']: selectionDict['zMass'] = (['z1.mass'], [60,60,120], cut) selectionDict['zMassFull'] = (['z1.mass'], [80,0,240], cut) selectionDict['zPt'] = (['z1.Pt'], [40,0,400], cut) selectionDict['zPt1'] = (['z1.Pt1'], [40,0,200], cut) selectionDict['zPt2'] = (['z1.Pt2'], [40,0,200], cut) selectionDict['zIso1'] = (['z1.Iso1'], [50,0,0.5], cut) selectionDict['zIso2'] = (['z1.Iso2'], [50,0,0.5], cut) selectionDict['zDR'] = (['z1.dR'], [60,0,6], cut) if analysis in ['Hpp3l','WZ']: selectionDict['wPt'] = (['w1.Pt'], [40,0,400], cut) selectionDict['wPt1'] = (['w1.Pt1'], [40,0,200], cut) selectionDict['wIso1'] = (['w1.Iso1'], [50,0,0.5], cut) selectionDict['wMass'] = (['w1.mass'], [40,0,200], cut) selectionDict['wDPhi'] = (['w1.dPhi'], [32,0,3.2], cut) numleps = { 'Hpp2l': 2, 'Z' : 2, 'TT' : 2, 'WZ' : 3, 'Hpp3l': 3, 'Hpp4l': 4, } nl = numleps[channel] for l in range(nl): name = 'l%i' % (l+1) for f in ['','e','m']: thisCut = cut if f: thisCut = cut + ' & %sFlv=="%s"' % (name,f) selectionDict['%sPt%s'%(name,f.upper())] = (['%s.Pt' %name], [40,0,200], thisCut) selectionDict['%sEta%s'%(name,f.upper())] = (['%s.Eta' %name], [30,-3.0,3.0], thisCut) selectionDict['%sPhi%s'%(name,f.upper())] = (['%s.Phi' %name], [30,-3.14159,3.14159], thisCut) selectionDict['%sIso%s'%(name,f.upper())] = (['%s.Iso' %name], [50,0,.5], thisCut) # setup plotter channels, leptons = getChannels(nl) ntuples = 'ntuples/%s_%sTeV_%s' % (analysis,period,channel) saves = '%s_%s_%sTeV' % (analysis,channel,period) intLumiMap = getIntLumiMap() finalStates, leptons = getChannels(nl) mergeDict = getMergeDict(period) plotter = Plotter(channel,ntupleDir=ntuples,saveDir=saves,period=period,mergeDict=mergeDict,scaleFactor=scaleFactor) allSamples = [os.path.basename(fname).rstrip('.root') for fname in glob.glob('%s/*'%ntuples)] bgSamples = [x for x in allSamples if 'data' not in x] dataSamples = [x for x in allSamples if 'data' in x] plotter.initializeBackgroundSamples(bgSamples) if dataSamples: plotter.initializeDataSamples(dataSamples) plotter.setIntLumi(intLumiMap[period]) histNames = bgSamples if dataSamples: histNames += ['data'] for sample in allSamples: logger.info('%s:%s:%iTeV: Sample %s' % (analysis, channel, period, sample)) infilename = '%s/%s.root' % (ntuples,sample) filehash = hashfile(infilename) savedir = '%s/%s' % (rootPath,sample) python_mkdir(savedir) savefilename = '%s/%s.root' %(savedir,filehash) if os.path.isfile(savefilename) and not force: continue # already exists, don't need to do anything savefile = ROOT.TFile(savefilename,'recreate') adir = savefile.mkdir(channel) adir.cd() for name, (variable, binning, selection) in selectionDict.iteritems(): logger.debug('%s:%s:%iTeV: Variable %s' % (analysis, channel, period, name)) hist = plotter.getHist(sample,variable,binning,selection,True) if not hist: continue hist.SetName(name) hist.Write() adir.cd() logger.info('%s:%s:%iTeV: Finished' % (analysis, channel, period)) savefile.Close() return 0
def sync(analysis,channel,period,**kwargs): '''Print sync information to file.''' runTau = kwargs.pop('runTau',False) blind = kwargs.pop('blind',True) doEfficiency = kwargs.pop('doEfficiency',False) doCutflow = kwargs.pop('doCutflow',False) doYields = kwargs.pop('doYields',False) doCounts = kwargs.pop('doCounts',False) doCorrelation = kwargs.pop('doCorrelation',False) doCategories = kwargs.pop('doCategories',False) doChargeId = kwargs.pop('doChargeId',False) do4l = kwargs.pop('do4l',False) doFinalStates = kwargs.pop('doFinalStates',False) doDataDriven = kwargs.pop('doDataDriven',True) cut = kwargs.pop('cut','1') bp = kwargs.pop('bp','') mass = kwargs.pop('mass',500) print '' print '%s:%s:%iTeV' % (analysis, channel, period) print 'Selection to be used:' print cut if analysis in ['Hpp3l','Hpp4l']: print 'Mass %i' % mass print '' sys.stdout.flush() # sync on WZ sample # sync on channels: eee, eem, emm, mmm ntuples = 'ntuples/%s_%sTeV_%s' % (analysis,period,channel) saves = '%s_%s_%sTeV' % (analysis,channel,period) mergeDict = getMergeDict(period) nl = 3 if analysis == 'WZ' or analysis == 'Hpp3l' else 4 finalStates, leptons = getChannels(nl) if analysis in ['WZ']: finalStates = ['eee','eem','mme','mmm'] s = 'Sig' if analysis in ['WZ']: s = 'WZ' if do4l: s = 'SigPP' sigMap = getSigMap(nl,mass) channelBackground = getChannelBackgrounds(period) plotter = Plotter(channel,ntupleDir=ntuples,saveDir=saves,period=period,mergeDict=mergeDict,dataDriven=doDataDriven) plotter.initializeBackgroundSamples([sigMap[period][x] for x in channelBackground[channel]]) if analysis in ['Hpp3l', 'Hpp4l']: plotter.initializeSignalSamples([sigMap[period][s]]) plotter.initializeDataSamples([sigMap[period]['data']]) intLumi = getIntLumiMap()[period] plotter.setIntLumi(intLumi) cutflowMap = defineCutFlowMap(analysis,finalStates,mass) cutflow = {} for c,l in zip(cutflowMap['cuts'],cutflowMap['labels_simple']): cutflow[l] = c cutflows = cutflowMap['labels_simple'] allMC = [x for x in channelBackground[channel] if x not in ['Z','TT','T']] + ['datadriven'] if doDataDriven else channelBackground[channel] if analysis in ['Hpp3l', 'Hpp4l']: allMC += [s] if doCounts: print '{0} signal event counts'.format(analysis) tempCut = cut for chan in finalStates: num = plotter.getNumEntries('%s&channel=="%s"' %(tempCut,chan), sigMap[period][s], doUnweighted=True, do4l=do4l, bp=bp) print '%s: %10.2f' % (chan, num) print '' sys.stdout.flush() if doCategories: labels = {0:'F',1:'T'} cuts = {0:'{0}.PassTight{1}==0',1:'{0}.PassTight{1}==1'} yields = {} yieldsMC = {} yieldsWeightedData = {} yieldsWeightedMC = {} yieldsWeighted = {} nameMap = { 0: 'z1.PassTight1', 1: 'z1.PassTight2', 2: 'w1.PassTight1', } effMap = { 0: 'z1.LepEffTight1', 1: 'z1.LepEffTight2', 2: 'w1.LepEffTight1', } fakeMap = { 0: 'z1.LepFake1', 1: 'z1.LepFake2', 2: 'w1.LepFake1', } if analysis in ['Hpp3l']: nameMap = { 0: 'h1.PassTight1', 1: 'h1.PassTight2', 2: 'h2.PassTight1', } effMap = { 0: 'h1.LepEffTight1', 1: 'h1.LepEffTight2', 2: 'h2.LepEffTight1', } fakeMap = { 0: 'h1.LepFake1', 1: 'h1.LepFake2', 2: 'h2.LepFake1', } #allCuts = 'finalstate.mass>100. && (z1.Pt1>20.&&z1.Pt2>10.) && z1.mass>60. && z1.mass<120. && w1.dR1_z1_1>0.1 && w1.dR1_z1_2>0.1 && w1.Pt1>20. && finalstate.met>30.' #allCuts = 'finalstate.mass>100. && (z1.Pt1>20.&&z1.Pt2>10.) && z1.mass>60. && z1.mass<120. && w1.mll_z1_1>4 && w1.mll_z1_2>4 && w1.Pt1>20. && finalstate.met>30.' allCuts = getPassTightDefinition(analysis,channel,period) if analysis in ['Hpp3l']: allCuts = '1' # no special cuts at select.passTight myCut = cut for l in range(3): myCut = myCut.replace(nameMap[l],'1') myCut = myCut.replace('l{0}.PassTight'.format(l),'1') myCut = myCut.replace('select.passTight',allCuts) #isocuts = ' && ((l{0}.Iso<0.4 && l{0}Flv=="e") || (l{0}.Iso<1.0 && l{0}Flv=="m"))' #for l in range(3): # myCut += isocuts.format(l+1) for chan in finalStates: yields[chan] = {} yieldsMC[chan] = {} yieldsWeighted[chan] = {} yieldsWeightedMC[chan] = {} yieldsWeightedData[chan] = {} for l1 in [0,1]: for l2 in [0,1]: for l3 in [0,1]: thisCut = '{0} && channel=="{1}" && '.format(myCut,chan) + ' && '.join([cuts[l1].format('z1','1'),cuts[l2].format('z1','2'),cuts[l3].format('w1','1')]) if analysis=='Hpp3l': thisCut = '{0} && channel=="{1}" && '.format(myCut,chan) + ' && '.join([cuts[l1].format('h1','1'),cuts[l2].format('h1','2'),cuts[l3].format('h2','1')]) #if not (l1 and l2 and l3): thisCut += ' && finalstate.bjetVeto30Medium==0' thisName = ''.join([labels[l1],labels[l2],labels[l3]]) yields[chan][thisName] = plotter.getDataEntries(thisCut) num = '1' if thisName.count('F') in [1,3] else '-1' for l in range(3): if thisName[l] == 'F': num += '*{0}'.format(fakeMap[l]) scalefactor = num if thisName=='TTT': scalefactor = '1' yieldsWeightedData[chan][thisName] = plotter.getDataEntries(thisCut,customScale=scalefactor) yieldsWeighted[chan][thisName] = yieldsWeightedData[chan][thisName] if thisName=='TTT': yieldsWeightedMC[chan][thisName] = 0. else: yieldsWeightedMC[chan][thisName] = 0. for bg in allMC: if bg in ['TT','Z','ZG','Sig']: continue mcscale = plotter.getScaleFactor() + '*' + scalefactor yieldsWeightedMC[chan][thisName] += plotter.getNumEntries(thisCut,sigMap[period][bg],customScale=mcscale) yieldsWeighted[chan][thisName] -= yieldsWeightedMC[chan][thisName] # yields in each channel if doYields: yieldsMC[chan][thisName] = {} #print 'MC Yields (scaled to %i pb-1)' % intLumi #theCut = '&'.join([cutflow[x] for x in cutflows]) #print 'Selection applied: %s' % thisCut #print '%8s | Channel | Yield' % chan for b in allMC: val = plotter.getNumEntries('%s&channel=="%s"' %(thisCut,chan), sigMap[period][b], do4l=do4l, bp=bp) yieldsMC[chan][thisName][b] = val #print ' | %10s | %10.2f' %(b,val) val = plotter.getDataEntries('%s&channel=="%s"' %(thisCut,chan), do4l=do4l, bp=bp) yieldsMC[chan][thisName]['data'] = val #print ' | %10s | %10i' %('Data',val) #print '' sys.stdout.flush() print 'Data events for each category' print 'CAT | {0}'.format(' | '.join(['{0:8}'.format(x) for x in finalStates + ['Total']])) for cat in ['TTT','TTF','TFT','FTT','TFF','FTF','FFT','FFF']: print '{0} | {1}'.format(cat,' | '.join(['{0:8d}'.format(int(yields[x][cat])) for x in finalStates])) + ' | {0:8d}'.format(sum([int(yields[x][cat]) for x in finalStates])) print '' print 'Weighted events: Data' print 'CAT | {0}'.format(' | '.join(['{0:8}'.format(x) for x in finalStates + ['Total']])) for cat in ['TTT','TTF','TFT','FTT','TFF','FTF','FFT','FFF']: print '{0} | {1}'.format(cat,' | '.join(['{0:8.2f}'.format(yieldsWeightedData[x][cat]) for x in finalStates])) + ' | {0:8.2f}'.format(sum([yieldsWeightedData[x][cat] for x in finalStates])) print '' print 'Weighted events: MC' print 'CAT | {0}'.format(' | '.join(['{0:8}'.format(x) for x in finalStates + ['Total']])) for cat in ['TTT','TTF','TFT','FTT','TFF','FTF','FFT','FFF']: print '{0} | {1}'.format(cat,' | '.join(['{0:8.2f}'.format(yieldsWeightedMC[x][cat]) for x in finalStates])) + ' | {0:8.2f}'.format(sum([yieldsWeightedMC[x][cat] for x in finalStates])) print '' print 'Weighted events: Total' print 'CAT | {0}'.format(' | '.join(['{0:8}'.format(x) for x in finalStates + ['Total']])) for cat in ['TTT','TTF','TFT','FTT','TFF','FTF','FFT','FFF']: print '{0} | {1}'.format(cat,' | '.join(['{0:8.2f}'.format(yieldsWeighted[x][cat]) for x in finalStates])) + ' | {0:8.2f}'.format(sum([yieldsWeighted[x][cat] for x in finalStates])) print '' sys.stdout.flush() if doYields: for chan in finalStates: print 'MC Yields: {0}'.format(chan) print 'CAT | {0}'.format(' | '.join(['{0:8}'.format(x) for x in allMC + ['Data']])) for cat in ['TTT','TTF','TFT','FTT','TFF','FTF','FFT','FFF']: print '{0} | {1}'.format(cat,' | '.join(['{0:8.2f}'.format(yieldsMC[chan][cat][x]) for x in allMC + ['data']])) print '' # yields in each channel if doYields: print 'Yields (scaled to %i pb-1)' % intLumi #theCut = '&'.join([cutflow[x] for x in cutflows]) print 'Selection applied: %s' % cut for chan in finalStates: print '%8s | Channel | Yield' % chan for b in allMC: val = plotter.getNumEntries('%s&channel=="%s"' %(cut,chan), sigMap[period][b], do4l=do4l, bp=bp) print ' | %10s | %10.2f' %(b,val) val = plotter.getDataEntries('%s&channel=="%s"' %(cut,chan), do4l=do4l, bp=bp) print ' | %10s | %10i' %('Data',val) print '' sys.stdout.flush() # cut flow if doCutflow: print 'Cutflows' for chan in finalStates: print '%15s | Sig | BG | S/B | Data' % chan for c in range(len(cutflows)): sig = 0 bg = 0 theCut = '&'.join([cutflow[x] for x in cutflows[0:c+1]]) for b in allMC: val = plotter.getNumEntries('%s&channel=="%s"' %(theCut,chan), sigMap[period][b], do4l=do4l, bp=bp) if b==s: sig += val elif 'data' in b: pass else: bg += val data = plotter.getDataEntries('%s&channel=="%s"' %(theCut,chan), do4l=do4l, bp=bp) print '%15s | %10.2f | %10.2f | %10.2f | %10i' %(cutflows[c],sig,bg,sig/bg,data) print '' sys.stdout.flush() # electron charge id efficiency if doChargeId: print 'Charge ID efficiency' bgNum = 0. bgNum_err_2 = 0. bgDenom = 0. bgDenom_err_2 = 0. sigNum = 0. sigNum_err_2 = 0. sigDenom = 0. sigDenom_err_2 = 0. dataNum = 0. dataNum_err_2 = 0. dataDenom = 0. dataDenom_err_2 = 0. for b in allMC + ['data']: val01, err01 = plotter.getNumEntries('%s & l1Flv=="e" & l1.ChargeConsistent==0' %cut, sigMap[period][b], doError=True, do4l=do4l, bp=bp) val02, err02 = plotter.getNumEntries('%s & l2Flv=="e" & l2.ChargeConsistent==0' %cut, sigMap[period][b], doError=True, do4l=do4l, bp=bp) val03, err03 = plotter.getNumEntries('%s & l3Flv=="e" & l3.ChargeConsistent==0' %cut, sigMap[period][b], doError=True, do4l=do4l, bp=bp) val11, err11 = plotter.getNumEntries('%s & l1Flv=="e" & l1.ChargeConsistent==1' %cut, sigMap[period][b], doError=True, do4l=do4l, bp=bp) val12, err12 = plotter.getNumEntries('%s & l2Flv=="e" & l2.ChargeConsistent==1' %cut, sigMap[period][b], doError=True, do4l=do4l, bp=bp) val13, err13 = plotter.getNumEntries('%s & l3Flv=="e" & l3.ChargeConsistent==1' %cut, sigMap[period][b], doError=True, do4l=do4l, bp=bp) val0 = val01+val02+val03 val1 = val11+val12+val13 err0_2 = err01**2 + err02**2 + err03**2 err1_2 = err11**2 + err12**2 + err13**2 if b==s: sigNum += val1 sigNum_err_2 += err1_2 sigDenom += val0 + val1 sigDenom_err_2 += err0_2 + err1_2 elif 'data' in b: dataNum += val1 dataNum_err_2 += err1_2 dataDenom += val0 + val1 dataDenom_err_2 += err0_2 + err1_2 else: bgNum += val1 bgNum_err_2 += err1_2 bgDenom += val0 + val1 bgDenom_err_2 += err0_2 + err1_2 sigEff = sigNum/sigDenom sigErr = (sigNum_err_2/sigNum**2 + sigDenom_err_2/sigDenom**2)**0.5 * sigEff bgEff = bgNum/bgDenom bgErr = (bgNum_err_2/bgNum**2 + bgDenom_err_2/bgDenom**2)**0.5 * bgEff dataEff = float(dataNum)/dataDenom dataErr = (dataNum_err_2/dataNum**2 + dataDenom_err_2/dataDenom**2)**0.5 * dataEff print 'Sig Efficiency: %f +/- %f, BG Efficiency: %f +/- %f, Data Efficiency: %f +/- %f' % (sigEff, sigErr, bgEff, bgErr, dataEff, dataErr) ptBins = [20.,30.,40.,60.,100.,1000.] for p in range(len(ptBins)-1): bgNum = 0. bgNum_err_2 = 0. bgDenom = 0. bgDenom_err_2 = 0. sigNum = 0. sigNum_err_2 = 0. sigDenom = 0. sigDenom_err_2 = 0. dataNum = 0. dataNum_err_2 = 0. dataDenom = 0. dataDenom_err_2 = 0. ptlow = ptBins[p] pthigh = ptBins[p+1] for b in allMC + ['data']: val01, err01 = plotter.getNumEntries('%s && l1Flv=="e" && l1.ChargeConsistent==0 && l1.Pt > %f && l1.Pt < %f' %(cut,ptlow,pthigh), sigMap[period][b], doError=True, do4l=do4l, bp=bp) val02, err02 = plotter.getNumEntries('%s && l2Flv=="e" && l2.ChargeConsistent==0 && l2.Pt > %f && l2.Pt < %f' %(cut,ptlow,pthigh), sigMap[period][b], doError=True, do4l=do4l, bp=bp) val03, err03 = plotter.getNumEntries('%s && l3Flv=="e" && l3.ChargeConsistent==0 && l3.Pt > %f && l3.Pt < %f' %(cut,ptlow,pthigh), sigMap[period][b], doError=True, do4l=do4l, bp=bp) val11, err11 = plotter.getNumEntries('%s && l1Flv=="e" && l1.ChargeConsistent==1 && l1.Pt > %f && l1.Pt < %f' %(cut,ptlow,pthigh), sigMap[period][b], doError=True, do4l=do4l, bp=bp) val12, err12 = plotter.getNumEntries('%s && l2Flv=="e" && l2.ChargeConsistent==1 && l2.Pt > %f && l2.Pt < %f' %(cut,ptlow,pthigh), sigMap[period][b], doError=True, do4l=do4l, bp=bp) val13, err13 = plotter.getNumEntries('%s && l3Flv=="e" && l3.ChargeConsistent==1 && l3.Pt > %f && l3.Pt < %f' %(cut,ptlow,pthigh), sigMap[period][b], doError=True, do4l=do4l, bp=bp) val0 = val01+val02+val03 val1 = val11+val12+val13 err0_2 = err01**2 + err02**2 + err03**2 err1_2 = err11**2 + err12**2 + err13**2 if b==s: sigNum += val1 sigNum_err_2 += err1_2 sigDenom += val0 + val1 sigDenom_err_2 += err0_2 + err1_2 elif 'data' in b: dataNum += val1 dataNum_err_2 += err1_2 dataDenom += val0 + val1 dataDenom_err_2 += err0_2 + err1_2 else: bgNum += val1 bgNum_err_2 += err1_2 bgDenom += val0 + val1 bgDenom_err_2 += err0_2 + err1_2 sigEff = sigNum/sigDenom sigErr = (sigNum_err_2/sigNum**2 + sigDenom_err_2/sigDenom**2)**0.5 * sigEff bgEff = bgNum/bgDenom bgErr = (bgNum_err_2/bgNum**2 + bgDenom_err_2/bgDenom**2)**0.5 * bgEff dataEff = float(dataNum)/dataDenom dataErr = (dataNum_err_2/dataNum**2 + dataDenom_err_2/dataDenom**2)**0.5 * dataEff sf = dataEff/bgEff sfErr = ((dataErr/dataEff)**2 + (bgErr/bgEff)**2)**0.5 * sf print 'Pt range: [%i, %i], Sig Efficiency: %f +/- %f, BG Efficiency: %f +/- %f, Data Efficiency: %f +/- %f, Data/BG: %f +/- %f' % (int(ptlow),int(pthigh),sigEff,sigErr,bgEff,bgErr,dataEff,dataErr,sf,sfErr) print '' # efficiency of cuts if doEfficiency: print 'Cut efficiencies' sigPreCuts = {} bgPreCuts = {} sigFullCuts = {} bgFullCuts = {} allSigPre = 0 allBgPre = 0 allSigFull = 0 allBgFull = 0 for chan in finalStates: sigPre = 0 bgPre = 0 sigFull = 0 bgFull = 0 theFullCut = '&'.join([cutflow[x] for x in cutflows]) for b in allMC: valPre = plotter.getNumEntries('%s&channel=="%s"' %(cut,chan), sigMap[period][b], do4l=do4l, bp=bp) valFull = plotter.getNumEntries('%s&channel=="%s"' %(theFullCut,chan), sigMap[period][b], do4l=do4l, bp=bp) if b==s: sigPre += valPre sigFull += valFull elif 'data' in b: pass else: bgPre += valPre bgFull += valFull sigPreCuts[chan] = sigPre bgPreCuts[chan] = bgPre sigFullCuts[chan] = sigFull bgFullCuts[chan] = bgFull allSigPre += sigPre allBgPre += bgPre allSigFull += sigFull allBgFull += bgFull sigPreCuts['all'] = allSigPre bgPreCuts['all'] = allBgPre sigFullCuts['all'] = allSigFull bgFullCuts['all'] = allBgFull for c in cutflows[1:]: print '%15s | Sg Pre Eff | BG Pre Eff | Sg Post Eff | BG Post Eff' % c allSigAllbut = 0 allBgAllbut = 0 allSigOnly = 0 allBgOnly = 0 for chan in finalStates: sigAllbut = 0 bgAllbut = 0 sigOnly = 0 bgOnly = 0 theCut = '&'.join([cutflow[x] for x in cutflows if x != c]) theOnlyCut = '%s&%s' % (cut, cutflow[c]) for b in allMC: valAllbut = plotter.getNumEntries('%s&channel=="%s"' %(theCut,chan), sigMap[period][b], do4l=do4l, bp=bp) valOnly = plotter.getNumEntries('%s&channel=="%s"' %(theOnlyCut,chan), sigMap[period][b], do4l=do4l, bp=bp) if b==s: sigAllbut += valAllbut sigOnly += valOnly elif 'data' in b: pass else: bgAllbut += valAllbut bgOnly += valOnly allSigAllbut += sigAllbut allBgAllbut += bgAllbut allSigOnly += sigOnly allBgOnly += bgOnly sigEffPre = sigOnly/sigPreCuts[chan] if sigPreCuts[chan] else -1 bgEffPre = bgOnly/bgPreCuts[chan] if bgPreCuts[chan] else -1 sigEffPost = sigFullCuts[chan]/sigAllbut if sigAllbut else -1 bgEffPost = bgFullCuts[chan]/bgAllbut if bgAllbut else -1 print '%15s | %11.4f | %11.4f | %11.4f | %11.4f' % (chan, sigEffPre, bgEffPre, sigEffPost, bgEffPost) chan = 'all' sigEffPre = allSigOnly/sigPreCuts[chan] if sigPreCuts[chan] else -1 bgEffPre = allBgOnly/bgPreCuts[chan] if bgPreCuts[chan] else -1 sigEffPost = sigFullCuts[chan]/allSigAllbut if allSigAllbut else -1 bgEffPost = bgFullCuts[chan]/allBgAllbut if allBgAllbut else -1 print '%15s | %11.4f | %11.4f | %11.4f | %11.4f' % (chan, sigEffPre, bgEffPre, sigEffPost, bgEffPost) print '' print 'Cut efficiencies' allPre = {} allFull = {} for chan in finalStates: allPre[chan] = {} allFull[chan] = {} theFullCut = '&'.join([cutflow[x] for x in cutflows]) for b in allMC: valPre = plotter.getNumEntries('%s&channel=="%s"' %(cut,chan), sigMap[period][b], do4l=do4l, bp=bp) valFull = plotter.getNumEntries('%s&channel=="%s"' %(theFullCut,chan), sigMap[period][b], do4l=do4l, bp=bp) allPre[chan][b] = valPre allFull[chan][b] = valFull allPre['all'] = {} allFull['all'] = {} for b in allMC: allPre['all'][b] = sum([allPre[x][b] for x in finalStates]) allFull['all'][b] = sum([allFull[x][b] for x in finalStates]) for c in cutflows[1:]: pre = ' | '.join(['{0:11}'.format(x+' Pre') for x in allMC]) post = ' | '.join(['{0:11}'.format(x+' Post') for x in allMC]) print '{0:15} | {1} | {2}'.format(c,pre,post) allBut = {} allOnly = {} allPreEff = {} allPostEff = {} for chan in finalStates: allBut[chan] = {} allOnly[chan] = {} allPreEff[chan] = {} allPostEff[chan] = {} theCut = '&'.join([cutflow[x] for x in cutflows if x != c]) theOnlyCut = '%s&%s' % (cut, cutflow[c]) for b in allMC: valAllbut = plotter.getNumEntries('%s&channel=="%s"' %(theCut,chan), sigMap[period][b], do4l=do4l, bp=bp) valOnly = plotter.getNumEntries('%s&channel=="%s"' %(theOnlyCut,chan), sigMap[period][b], do4l=do4l, bp=bp) allBut[chan][b] = valAllbut allOnly[chan][b] = valOnly allPreEff[chan][b] = allOnly[chan][b]/allPre[chan][b] if allPre[chan][b] else -1 allPostEff[chan][b] = allFull[chan][b]/allBut[chan][b] if allBut[chan][b] else -1 pre = ' | '.join(['{0:11.4f}'.format(allPreEff[chan][x]) for x in allMC]) post = ' | '.join(['{0:11.4f}'.format(allPostEff[chan][x]) for x in allMC]) print '{0:15} | {1} | {2}'.format(chan, pre, post) allBut['all'] = {} allOnly['all'] = {} allPreEff['all'] = {} allPostEff['all'] = {} for b in allMC: allBut['all'][b] = sum([allBut[x][b] for x in finalStates]) allOnly['all'][b] = sum([allOnly[x][b] for x in finalStates]) allPreEff['all'][b] = allOnly['all'][b]/allPre['all'][b] if allPre['all'][b] else -1 allPostEff['all'][b] = allFull['all'][b]/allBut['all'][b] if allBut['all'][b] else -1 pre = ' | '.join(['{0:11.4f}'.format(allPreEff['all'][x]) for x in allMC]) post = ' | '.join(['{0:11.4f}'.format(allPostEff['all'][x]) for x in allMC]) print '{0:15} | {1} | {2}'.format('all', pre, post) print '' if doCorrelation: print 'Correlation matrix' for chan in finalStates: print ' | '.join(['%15s'%(chan+' denom.')] + ['%15s' % x for x in cutflows[1:]]) for dc in cutflows[1:]: row = [] for nc in cutflows[1:]: numCut = '%s & %s & %s' % (cut, cutflow[dc], cutflow[nc]) denomCut = '%s & %s' % (cut, cutflow[dc]) numSig = plotter.getNumEntries('%s&channel=="%s"' %(numCut,chan), sigMap[period][s], do4l=do4l, bp=bp) denomSig = plotter.getNumEntries('%s&channel=="%s"' %(denomCut,chan), sigMap[period][s], do4l=do4l, bp=bp) eff = numSig/denomSig if denomSig else -1 row += [eff] print ' | '.join(['%15s'%dc] + ['%15.4f' % x for x in row]) print ''
def getChargeSystematic(analysis,channel,runPeriod,**kwargs): '''A function to simplify plotting multiple channels and run periods.''' mass = kwargs.pop('mass',500) myCut = kwargs.pop('myCut','1') scaleFactor = kwargs.pop('scaleFactor','event.pu_weight*event.lep_scale*event.trig_scale') loglevel = kwargs.pop('loglevel','INFO') for key, value in kwargs.iteritems(): logger.warning("Unrecognized parameter '" + key + "' = " + str(value)) return 0 logging.info("%s:%s:%iTeV: Mass: %i" % (analysis,channel,runPeriod,mass)) numleps = { 'Hpp2l': 2, 'Z' : 2, 'TT' : 2, 'WZ' : 3, 'WZ_W' : 1, 'WZ_Dijet': 1, 'Hpp3l': 3, 'Hpp4l': 4, } nl = numleps[analysis] ntuples = 'ntuples/%s_%sTeV_%s' % (analysis,runPeriod,channel) saves = '%s_%s_%sTeV' % (analysis,channel,runPeriod) sigMap = getSigMap(nl,mass) intLumiMap = getIntLumiMap() channelBackground = getChannelBackgrounds(runPeriod) finalStates, leptons = getChannels(nl) mergeDict = getMergeDict(runPeriod) cutFlowMap = {} cutFlowMap[channel] = defineCutFlowMap(channel,finalStates,mass) plotter = Plotter(channel,ntupleDir=ntuples,saveDir=saves,period=runPeriod,mergeDict=mergeDict,scaleFactor=scaleFactor,loglevel=loglevel,rootName='charge_sys') plotter.initializeBackgroundSamples([sigMap[runPeriod][x] for x in channelBackground[channel]]) plotter.initializeSignalSamples([sigMap[runPeriod]['Sig']]) plotter.initializeDataSamples([sigMap[runPeriod]['data']]) plotter.setIntLumi(intLumiMap[runPeriod]) systMap = {} for numElec in range(nl+1): logging.info('%s:%s:%iTeV: Num electrons: %i' % (analysis, channel, runPeriod, numElec)) systMap[numElec] = {} states = [x for x in finalStates if x.count('e')==numElec] chanCuts = ['channel=="{0}"'.format(x) for x in states] chanCut = ' || '.join(chanCuts) cut = '{0} && ({1})'.format(myCut,chanCut) sig_num = plotter.getSignalEntries(cut,customScale='event.pu_weight*event.lep_scale*event.trig_scale*event.charge_uncertainty') bg_num = plotter.getBackgroundEntries(cut,customScale='event.pu_weight*event.lep_scale*event.trig_scale*event.charge_uncertainty') data_num = plotter.getDataEntries(cut,customScale='charge_uncertainty') sig_den = plotter.getSignalEntries(cut) bg_den = plotter.getBackgroundEntries(cut) data_den = plotter.getDataEntries(cut) sig_syst = sig_num/sig_den if sig_den else 1. bg_syst = bg_num/bg_den if bg_den else 1. data_syst = data_num/data_den if data_den else 1. systMap[numElec]['sig'] = sig_syst systMap[numElec]['bg'] = bg_syst systMap[numElec]['data'] = data_syst return systMap
def main(argv=None): loglevel = getattr(logging,'INFO') logging.basicConfig(format='%(asctime)s.%(msecs)03d %(levelname)s %(name)s: %(message)s', level=loglevel, datefmt='%Y-%m-%d %H:%M:%S') logger = logging.getLogger(__name__) nl = 2 mass = 500 analysis = 'Hpp2l' runPeriod = 8 channel = 'Charge' ntuples = 'ntuples/%s_%iTeV_%s' % (analysis,runPeriod,channel) saves = '%s_%s_%sTeV' % (analysis,channel,runPeriod) sigMap = getSigMap(nl,mass) intLumiMap = getIntLumiMap() channelBackground = getChannelBackgrounds(runPeriod) finalStates, leptons = getChannels(nl) mergeDict = getMergeDict(runPeriod) logger.info('Load plotter') plotter = Plotter(channel,ntupleDir=ntuples,saveDir=saves,period=runPeriod,mergeDict=mergeDict,rootName='chargeId') plotter.initializeBackgroundSamples([sigMap[runPeriod]['Z']]) #plotter.initializeBackgroundSamples([sigMap[runPeriod][x] for x in channelBackground[channel]]) plotter.initializeDataSamples([sigMap[runPeriod]['data']]) plotter.setIntLumi(intLumiMap[runPeriod]) plotMode = 'plotMCData' plotMethod = getattr(plotter,plotMode) results = {'e': {}, 'm': {}} myCut = 'finalstate.met<20.' samesign = 'l1.Chg==l2.Chg && {0}'.format(myCut) oppsign = 'l1.Chg!=l2.Chg && {0}'.format(myCut) logger.info('Calculate values') ptBins = [10.,20.,30.,40.,60.,100.,200.] etaBins = { 'e': [0,1.479,2.5], 'm': [0,1.2,2.4], } for l in ['e']: flv = 'z1Flv=="{0}" && fabs(z1.mass-91.1876)<10.'.format(l+l) results[l] = {'ss':{},'os':{},'unc':{},} for p in range(len(ptBins)-1): logger.info('{0}: pT {1:f}-{2:f}'.format(l,ptBins[p],ptBins[p+1])) # tag first lepton, probe second, both in same eta region ptcut = 'l2.Pt>={0:f} && l2.Pt<{1:f}'.format(ptBins[p],ptBins[p+1]) for e in range(len(etaBins[l])-1): logger.info('{0}: eta {1:f}-{2:f}'.format(l,etaBins[l][e],etaBins[l][e+1])) etacut = 'fabs(l1.Eta)>={0:f} && fabs(l1.Eta)<{1:f} && fabs(l2.Eta)>={0:f} && fabs(l2.Eta)<{1:f}'.format(etaBins[l][e],etaBins[l][e+1]) mc = 'mc{0}{1}'.format(p,e) data = 'data{0}{1}'.format(p,e) thisCut = '{0} && {1} && {2} && {3}'.format(samesign,flv,ptcut,etacut) results[l]['ss'][mc] = plotter.getBackgroundEntries(thisCut,doError=True) results[l]['ss'][data] = plotter.getDataEntries(thisCut,doError=True) logger.info('{0}: Same sign: MC: {1:f} +/- {2:f}; Data: {3:f} +/- {4:f}'.format(l,results[l]['ss'][mc][0],results[l]['ss'][mc][1],results[l]['ss'][data][0],results[l]['ss'][data][1])) plotMethod('z1.mass', [60,60,120], 'z1Mass_samesign_{0}_{1}_{2}'.format(l,p,e), yaxis='Events/1.0 GeV', xaxis='M_{\\ell^{+}\\ell^{+}} (GeV)', legendpos=43,logy=0,cut=thisCut) thisCut = '{0} && {1} && {2} && {3}'.format(oppsign,flv,ptcut,etacut) results[l]['os'][mc] = plotter.getBackgroundEntries(thisCut,doError=True) results[l]['os'][data] = plotter.getDataEntries(thisCut,doError=True) logger.info('{0}: Opposite sign: MC: {1:f} +/- {2:f}; Data: {3:f} +/- {4:f}'.format(l,results[l]['os'][mc][0],results[l]['os'][mc][1],results[l]['os'][data][0],results[l]['os'][data][1])) plotMethod('z1.mass', [60,60,120], 'z1Mass_oppositesign_{0}_{1}_{2}'.format(l,p,e), yaxis='Events/1.0 GeV', xaxis='M_{\\ell^{+}\\ell^{-}} (GeV)', legendpos=43,logy=0,cut=thisCut) mcnum = results[l]['ss'][mc] mcdenom = getSum(results[l]['ss'][mc],results[l]['os'][mc]) mcratio = getRatio(mcnum,mcdenom) results[l]['unc'][mc] = mcratio datanum = results[l]['ss'][data] datadenom = getSum(results[l]['ss'][data],results[l]['os'][data]) dataratio = getRatio(datanum,datadenom) results[l]['unc'][data] = dataratio ratio = getRatio(results[l]['unc'][data],results[l]['unc'][mc]) logger.info('{0}: Uncertainty: MC: {1:f} +/- {2:f}; Data: {3:f} +/- {4:f}; Data/MC: {5:f} +/- {6:f}'.format(l,results[l]['unc'][mc][0],results[l]['unc'][mc][1],results[l]['unc'][data][0],results[l]['unc'][data][1],ratio[0],ratio[1])) print json.dumps(results,sort_keys=True,indent=4)