Пример #1
0
float deltaR(LorentzVector jet1, LorentzVector jet2){
  // From cmssw reco::deltaPhi()
  float dphi = jet1.Phi() - jet2.Phi();
  while( dphi >   TMath::Pi() ) dphi -= TMath::TwoPi();
  while( dphi <= -TMath::Pi() ) dphi += TMath::TwoPi();
  return TMath::Sqrt(TMath::Power(dphi,2)+TMath::Power(jet1.Eta()-jet2.Eta(),2));
}
Пример #2
0
void Content() {
  
  bool signal = false;
  TString bgdInputFile    = "/data/smurf/data/Run2012_Summer12_SmurfV9_53X/mitf-alljets/backgroundA_3l.root";
  //TString bgdInputFile   =  "/data/smurf/data/Run2012_Summer12_SmurfV9_53X/mitf-alljets/zhww125.root";

  
  //Load datasets
  SmurfTree background;
  background.LoadTree(bgdInputFile,-1);
  background.InitTree(0);
  
  char output[200];
  sprintf(output,"rootfiles/composition_study.root");     
  TFile* outFileNjets = new TFile(output,"recreate");
 
 
  TH1D* bck_cuts = new TH1D("bck_cuts", "cuts", 10, 0, 10);
  
  bck_cuts->Sumw2();
   double eventsPassBck = 0;
   double weight = 1;
     //Backgrounds
  double bckType[62] = {0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,
			0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,
			0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,
			0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.};

  double weiType[62] = {0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,
			0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,
			0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,
			0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.,0.};
  
  TString bckName[62] = {"null","null","null","null","null","null","null","null","null","null","null","null","null","null","null",
                         "null","null","null","null","null","null","null","null","null","null","null","null","null","null","null",
                         "null","null","null","null","null","null","null","null","null","null","null","null","null","null","null",
                         "null","null","null","null","null","null","null","null","null","null","null","null","null","null","null", "null", "fakes"};
  
  bckName[0] = "data";
  bckName[1] = "qqww";
  bckName[2] = "ggww";
  bckName[43] = "ttbar";
  bckName[44] = "tw";
  bckName[46] = "dymm";
  bckName[49] = "wz";
  bckName[50] = "zz";
  bckName[51] = "wgamma";
  bckName[59] = "www";
  bckName[60] = "dyttdd";   
  int nBck=background.tree_->GetEntries();
  for (int i=0; i<nBck; ++i) {
    
    
    if (i%100000 == 0 && verboseLevel > 0)
      printf("--- reading event %5d of %5d\n",i,nBck);
    background.tree_->GetEntry(i);
 
 
    if(signal && background.processId_ != 24) continue;

    weight = 1;
    if (background.dstype_ != SmurfTree::data) weight = lumi*background.scale1fb_*background.sfWeightPU_*background.sfWeightEff_*background.sfWeightTrig_;    

    int nsel = background.dstype_;
  
    //Three real leptons MC level
    bool isRealLepton = false;
    if((TMath::Abs(background.lep1McId_) == 11 || TMath::Abs(background.lep1McId_) == 13) &&
       (TMath::Abs(background.lep2McId_) == 11 || TMath::Abs(background.lep2McId_) == 13) &&
       (TMath::Abs(background.lep3McId_) == 11 || TMath::Abs(background.lep3McId_) == 13)) isRealLepton = true; 
    if (!isRealLepton && background.dstype_ != SmurfTree::data) continue;
     
    //Check for fakes
    int nFake = 0;
    if(((background.cuts_ & SmurfTree::Lep1LooseMuV2)  == SmurfTree::Lep1LooseMuV2)  && (background.cuts_ & SmurfTree::Lep1FullSelection) != SmurfTree::Lep1FullSelection) nFake++;
    if(((background.cuts_ & SmurfTree::Lep2LooseMuV2)  == SmurfTree::Lep2LooseMuV2)  && (background.cuts_ & SmurfTree::Lep2FullSelection) != SmurfTree::Lep2FullSelection) nFake++;
    if(((background.cuts_ & SmurfTree::Lep3LooseMuV2)  == SmurfTree::Lep3LooseMuV2)  && (background.cuts_ & SmurfTree::Lep3FullSelection) != SmurfTree::Lep3FullSelection) nFake++;
    if(((background.cuts_ & SmurfTree::Lep1LooseEleV4) == SmurfTree::Lep1LooseEleV4) && (background.cuts_ & SmurfTree::Lep1FullSelection) != SmurfTree::Lep1FullSelection) nFake++;
    if(((background.cuts_ & SmurfTree::Lep2LooseEleV4) == SmurfTree::Lep2LooseEleV4) && (background.cuts_ & SmurfTree::Lep2FullSelection) != SmurfTree::Lep2FullSelection) nFake++;
    if(((background.cuts_ & SmurfTree::Lep3LooseEleV4) == SmurfTree::Lep3LooseEleV4) && (background.cuts_ & SmurfTree::Lep3FullSelection) != SmurfTree::Lep3FullSelection) nFake++;
   
    if (nFake){ 
      nsel = 61;
      double factor = 1;
      weight*= background.sfWeightFR_*factor;
      //if (background.dstype_ != SmurfTree::data) weight *=-1;
    }
    
    bck_cuts->Fill(0., weight);
    if (signal & nFake) continue;
    
    
    
    //2 same flavor, oppposite sign leptons + extra one
    if (background.lid3_ == background.lid2_ && background.lid3_ == background.lid1_) continue;
    if (background.lid3_ == background.lid2_ && fabs(background.lid3_) != fabs(background.lid1_)) continue;
    if (background.lid3_ == background.lid1_ && fabs(background.lid3_) != fabs(background.lid2_)) continue;
    if (background.lid2_ == background.lid1_ && fabs(background.lid2_) != fabs(background.lid3_)) continue;
    
    //Select the different things: Z pair, extra lepton, Higgs system
    int idcat = 20; // 0 = eee, 1 = eemu, 2 = mumue, 3 = mumumu
    if (fabs(background.lid1_) == 11 && fabs(background.lid2_) == 11 && fabs(background.lid3_) == 11) idcat = 0;
    else if ((fabs(background.lid1_) == 11 && fabs(background.lid2_) == 11 && fabs(background.lid3_) == 13) 
          || (fabs(background.lid1_) == 11 && fabs(background.lid2_) == 13 && fabs(background.lid3_) == 11) 
	  || (fabs(background.lid1_) == 13 && fabs(background.lid2_) == 11 && fabs(background.lid3_) == 11)) idcat = 1;
    else if ((fabs(background.lid1_) == 11 && fabs(background.lid2_) == 13 && fabs(background.lid3_) == 13) 
          || (fabs(background.lid1_) == 13 && fabs(background.lid2_) == 13 && fabs(background.lid3_) == 11) 
	  || (fabs(background.lid1_) == 13 && fabs(background.lid2_) == 11 && fabs(background.lid3_) == 13)) idcat = 2;
    else  if (fabs(background.lid1_) == 13 && fabs(background.lid2_) == 13 && fabs(background.lid3_) == 13)  idcat = 3;
    
   
       
     bck_cuts->Fill(1., weight);
    
    //At least 2 jets
    if (background.njets_ < 2 ) continue; 
    bck_cuts->Fill(2., weight);
   
    
    //Make z-compatible pairs
    double m[3] = {0, 0, 0};
    LorentzVector pair1, pair2, pair3, trilep;
    if (fabs(background.lid1_) == fabs(background.lid2_) && background.lq1_*background.lq2_ < 0){
      pair1 = background.lep1_ + background.lep2_ ;
      m[0] = pair1.M();
    }
    if (fabs(background.lid2_) == fabs(background.lid3_) && background.lq2_*background.lq3_ < 0){
      pair2 = background.lep2_ + background.lep3_ ;
      m[1] = pair2.M();
    }
    if (fabs(background.lid1_) == fabs(background.lid3_) && background.lq1_*background.lq3_ < 0){
      pair3 = background.lep1_ + background.lep3_ ;
      m[2] = pair3.M();
    }
    trilep = background.lep1_ + background.lep2_ + background.lep3_ ;

    
    //Get the closest to the Z mass
    double min = TMath::Min(TMath::Min(fabs(mz -m[0]), fabs(mz-m[1])), TMath::Min(fabs(mz -m[0]), fabs(mz-m[2])));
    
    //Select the different things: Z pair, extra lepton, Higgs system
    LorentzVector pair, tlepton, pairjet;
    double mt = 0;
    double dR = 0;
    if (min == fabs(mz - m[0])) {  pair = pair1; mt =  background.mt3_; tlepton = background.lep3_; dR = fabs(ROOT::Math::VectorUtil::DeltaR(background.lep1_ ,background.lep2_));} 
    else if (min == fabs(mz - m[1])){  pair = pair2;  mt =  background.mt1_; tlepton = background.lep1_; dR = fabs(ROOT::Math::VectorUtil::DeltaR(background.lep2_ ,background.lep3_));} 
    else if (min == fabs(mz - m[2])){  pair = pair3;  mt =  background.mt2_; tlepton = background.lep2_; dR = fabs(ROOT::Math::VectorUtil::DeltaR(background.lep1_ ,background.lep3_));} 
    pairjet = background.jet1_+ background.jet2_;
    LorentzVector metvector(background.met_*cos(background.metPhi_), background.met_*sin(background.metPhi_), 0, 0);
    LorentzVector higgsSystem = tlepton + metvector + background.jet1_+ background.jet2_;
    LorentzVector lm = tlepton + metvector;
   
      
    double hp[5];
    hp[0] = tlepton.Px() + background.jet1_.Px()+ background.jet2_.Px()+ metvector.Px();
    hp[1] = tlepton.Py() + background.jet1_.Py()+ background.jet2_.Py()+ metvector.Py();
    hp[2] = tlepton.Pz() + background.jet1_.Pz()+ background.jet2_.Pz()+ metvector.Pz();
    
    //Calculate p of the neutrino using Maria's code
    double metp = 0;
    double otherSol = 0;
    double alpha=(mw*mw-mmu*mmu)/2/tlepton.P()+(tlepton.Px()*background.met_*cos(background.metPhi_)+tlepton.Py()*background.met_*sin(background.metPhi_))/tlepton.P();
    double A=tlepton.Pz()*tlepton.Pz()/tlepton.P()/tlepton.P()-1;
    double B=2*alpha*tlepton.Pz()/tlepton.P();
    double C=alpha*alpha-(background.met_*cos(background.metPhi_)*background.met_*cos(background.metPhi_) + background.met_*sin(background.metPhi_)*background.met_*sin(background.metPhi_));
    bool isComplex = false;
    double tmproot = B*B - 4.0*A*C;
      if (tmproot<0) { 
        isComplex= true;
        metp = - B/(2*A); 
	otherSol = metp;
      } else {
        isComplex = false;
	double tmpsol1 = (-B + TMath::Sqrt(tmproot))/(2.0*A);
	double tmpsol2 = (-B - TMath::Sqrt(tmproot))/(2.0*A);
	if (TMath::Abs(tmpsol1)<TMath::Abs(tmpsol2) ) {
	  metp = tmpsol1; otherSol = tmpsol2; 
	} else { metp = tmpsol2; otherSol = tmpsol1; }
     }
   
    
   // hp[3] = tlepton.P() + background.jet1_.P()+ background.jet2_.P()+ metvector.P(); //crappy solution
    hp[3] = tlepton.P() + background.jet1_.P()+ background.jet2_.P()+ metp;
    hp[4] = tlepton.Pt() + background.jet1_.Pt()+ background.jet2_.Pt()+ background.met_;
    
    double recomh  = hp[3]*hp[3]-hp[0]*hp[0]-hp[1]*hp[1]-hp[2]*hp[2]; if(recomh  > 0) recomh  = sqrt(recomh);else recomh   = 0.0;
    double recomth = hp[4]*hp[4]-hp[0]*hp[0]-hp[1]*hp[1]; if(recomth > 0) recomth = sqrt(recomth); else recomth  = 0.0;
    
 
    //Kinematic cuts
    if (pair.M() < (mz - separation)|| pair.M() > (mz + separation)) continue; 
    bck_cuts->Fill(3., weight); 
       
    
    if (background.met_ < metcut) continue;
    bck_cuts->Fill(4., weight);
       
     
    
    if (mt > mtcut) continue;
    bck_cuts->Fill(5., weight);
    
    
    if (pairjet.M() < (mw - separationjj) || pairjet.M() > (mw + separationjj)) continue;
    bck_cuts->Fill(6., weight);
  
   //double deltaPhi = fabs(DeltaPhi(pairjet.Phi(),tlepton.Phi()));
    double deltaPhi = fabs(DeltaPhi(pairjet.Phi(),lm.Phi()));
    if (deltaPhi > phicut) continue;
    bck_cuts->Fill(7., weight);
  
    eventsPassBck += weight;
    
	     
    bckType[(int)nsel] += weight;
    weiType[(int)nsel] += weight*weight;	
   

  }
  
  cout << endl;
  cout << eventsPassBck << " background events in " << lumi << " fb" << endl; 
  cout << endl;


  
  if (verboseLevel){ 
    cout << "------------------------------------------" << endl;
    cout << "[Backgrounds (All mixed):] " << endl;
    cout << "------------------------------------------" << endl;  
    for (int i = 1; i < 9; i++){
      if (i == 1) cout << " 3 lep:\t\t" <<  bck_cuts->GetBinContent(i) << " +/-  " <<  bck_cuts->GetBinError(i)  << endl;
      if (i == 2) cout << " OSSF:\t\t" <<  bck_cuts->GetBinContent(i) << " +/-  " <<  bck_cuts->GetBinError(i)  << endl;
      if (i == 3) cout << " 2 jet:\t\t" <<  bck_cuts->GetBinContent(i) << " +/-  " <<  bck_cuts->GetBinError(i)  << endl;
      if (i == 4) cout << " mll:\t\t" <<  bck_cuts->GetBinContent(i) << " +/-  " <<  bck_cuts->GetBinError(i)  << endl;
      if (i == 5) cout << " met:\t\t" <<  bck_cuts->GetBinContent(i) << " +/-  " <<  bck_cuts->GetBinError(i)  << endl;
      if (i == 6) cout << " mt:\t\t" <<  bck_cuts->GetBinContent(i) << " +/-  " <<  bck_cuts->GetBinError(i)  << endl;
      if (i == 7) cout << " mjj:\t\t" <<  bck_cuts->GetBinContent(i) << " +/-  " <<  bck_cuts->GetBinError(i)  << endl;
      if (i == 8) cout << " phi:\t\t" <<  bck_cuts->GetBinContent(i) << " +/-  " <<  bck_cuts->GetBinError(i)  << endl;
    }
    cout << endl;
    cout << "[Breakdown:] " << endl;
    for(int i=0; i<62; i++){
      if(bckType[i] != 0 )
	cout << i <<"\t" << bckName[i] << ":\t\t" << bckType[i] << "+-" << sqrt(weiType[i]) <<endl;
    }
    cout << "------------------------------------------" << endl; 
  }
  
  outFileNjets->Write();
  outFileNjets->Close();
  
}
Пример #3
0
void chain(int cem = 8, int nsel = 0, double mh = 125, int mode = 0){

  char plotName[300];
  sprintf(plotName,"test");
  bool isBackground = true;
  bool isData = false;
		  
  if (nsel == 0)                	{sprintf(plotName,"Data");	isBackground = false;	isData = true;}
  else if (nsel == 1)   		{sprintf(plotName,"ZH");	isBackground = false;}
  else if (nsel == 2)   		{sprintf(plotName,"WZ");}
  else if (nsel == 3)   		{sprintf(plotName,"ZZ");}
  else if (nsel == 4)   		{sprintf(plotName,"VVV");}
  else if (nsel == 5)			{sprintf(plotName,"Wjets");}
  else if (nsel == 6) 			{sprintf(plotName, "all");}
  else if (nsel == 7) 			{sprintf(plotName, "ZH_SM");	isBackground = false;} //no fakes allowed
				  
  char myRootFile[300];
  if (cem != 7 && cem !=8) cem = 8;
  double lumi = lumi8;
 if (cem == 8){
    if (nsel == 0) sprintf(myRootFile,"/data/smurf/data/Run2012_Summer12_SmurfV9_53X/mitf-alljets/data_3l.root");
    else if (nsel == 7) sprintf(myRootFile,"/data/smurf/data/Run2012_Summer12_SmurfV9_53X/mitf-alljets/zhww125.root");
    else if (nsel == 1 && (mh == 125 || mh == 124 || mh == 126 || mh == 125.7)) sprintf(myRootFile,"/data/smurf/data/Run2012_Summer12_SmurfV9_53X/mitf-alljets/zhww125.root");
    else if (nsel == 1 && (mh == 118 || mh == 122)) sprintf(myRootFile,"/data/smurf/data/Run2012_Summer12_SmurfV9_53X/mitf-alljets/hww120.root");
    else if (nsel == 1 &&  mh == 128) sprintf(myRootFile,"/data/smurf/data/Run2012_Summer12_SmurfV9_53X/mitf-alljets/hww130.root");
    else if (nsel == 1) sprintf(myRootFile,"/data/smurf/data/Run2012_Summer12_SmurfV9_53X/mitf-alljets/hww%g.root", mh);
    else sprintf(myRootFile,"/data/smurf/data/Run2012_Summer12_SmurfV9_53X/mitf-alljets/backgroundA_3l.root");
  } else {
    lumi = lumi7;
    if (nsel == 0) sprintf(myRootFile,"/data/smurf/data/Run2011_Fall11_SmurfV9_42X/mitf-alljets/data_3l.root");
    else if (nsel == 7) sprintf(myRootFile,"/data/smurf/data/Run2011_Fall11_SmurfV9_42X/mitf-alljets/zhww125.root");
    else if (nsel == 1 && (mh == 125 || mh == 125.7)) sprintf(myRootFile,"/data/smurf/data/Run2011_Fall11_SmurfV9_42X/mitf-alljets/zhww125.root");
    else if (nsel == 1 && (mh == 110 || mh == 115)) sprintf(myRootFile,"/data/smurf/data/Run2011_Fall11_SmurfV9_42X/mitf-alljets/vtthww118.root");
    else if (nsel == 1 && mh == 145) sprintf(myRootFile,"/data/smurf/data/Run2011_Fall11_SmurfV9_42X/mitf-alljets/vtthww140.root");
    else if (nsel == 1) sprintf(myRootFile,"/data/smurf/data/Run2011_Fall11_SmurfV9_42X/mitf-alljets/vtthww%g.root", mh);
    else sprintf(myRootFile,"/data/smurf/data/Run2011_Fall11_SmurfV9_42X/mitf-alljets/backgroundA_3l.root");
  }
  
  cout << "[Info:] "<< cem <<  "TeV, " << plotName << ", Higgs mass " << mh << ","  ;
  if (mode == 1) cout << " eee channel" << endl ;
  else if (mode == 2) cout << " eem channel" << endl ; 
  else if (mode == 3) cout << " emm channel" << endl ; 
  else if (mode == 4) cout << " mmm channel" << endl ; 
  else cout << " all final states" << endl;
 								    
  //Load datasets
  SmurfTree sample;
  cout << myRootFile << endl;
  sample.LoadTree(myRootFile,-1);
  sample.InitTree(0);

  // Prepare output file
  char rootFile[300];
  if (mode == 1) sprintf(rootFile,"%g/zh3l2j_input_shape_eee_%dTeV.root", mh, cem);
  else if (mode == 2) sprintf(rootFile,"%g/zh3l2j_input_shape_eem_%dTeV.root", mh, cem);
  else if (mode == 3) sprintf(rootFile,"%g/zh3l2j_input_shape_emm_%dTeV.root", mh, cem);
  else if (mode == 4) sprintf(rootFile,"%g/zh3l2j_input_shape_mmm_%dTeV.root", mh, cem);
  else sprintf(rootFile,"%g/zh3l2j_input_shape_%dTeV.root", mh, cem);
  
  TFile f_root(rootFile, "UPDATE");
											      
  // Prepare histograms
  char title[300];
												    
  sprintf(title,"histo_%s",plotName);
  TH1F* histo = new TH1F( title, " ", nbins, nbinlow, nbinhigh);
  histo->Sumw2();

  //Prepare useful things
  double weight = 1;
  double eventsPass = 0;
														  
  int nSample=sample.tree_->GetEntries();
  for (int i=0; i<nSample; ++i) {
														           
    if (i%100000 == 0 && verboseLevel > 0)
      printf("--- reading event %5d of %5d\n",i,nSample);
    sample.tree_->GetEntry(i);
    
    if(nsel == 1 && sample.processId_ != 24) continue;
    if(nsel == 7 && sample.processId_ != 24) continue;

    //Modes, 0 = all, 1 = eee, 2 = eem, 3 = emm, 4 = mmm
    if (mode == 1 && (abs(sample.lid1_)!= 11 || abs(sample.lid2_) != 11 || abs(sample.lid3_) != 11)) continue;
    if (mode == 2 && 
       ((abs(sample.lid1_)!= abs(sample.lid2_) && abs(sample.lid1_) != abs(sample.lid3_) && abs(sample.lid1_) == 11) ||
        (abs(sample.lid2_)!= abs(sample.lid1_) && abs(sample.lid2_) != abs(sample.lid3_) && abs(sample.lid2_) == 11) ||
	(abs(sample.lid3_)!= abs(sample.lid1_) && abs(sample.lid3_) != abs(sample.lid2_) && abs(sample.lid3_) == 11) ||
	(abs(sample.lid1_) == abs(sample.lid2_) && abs(sample.lid1_) == abs(sample.lid3_)))) continue;
    if (mode == 3 && 
       ((abs(sample.lid1_)!= abs(sample.lid2_) && abs(sample.lid1_) != abs(sample.lid3_) && abs(sample.lid1_) == 13) ||
        (abs(sample.lid2_)!= abs(sample.lid1_) && abs(sample.lid2_) != abs(sample.lid3_) && abs(sample.lid2_) == 13) ||
	(abs(sample.lid3_)!= abs(sample.lid1_) && abs(sample.lid3_) != abs(sample.lid2_) && abs(sample.lid3_) == 13) ||
	(abs(sample.lid1_) == abs(sample.lid2_) && abs(sample.lid1_) == abs(sample.lid3_)))) continue;
    if (mode == 4 && (abs(sample.lid1_)!= 13 || abs(sample.lid2_) != 13 || abs(sample.lid3_) != 13)) continue;
   
    				     
    weight = 1;
    if (!isData && sample.dstype_ != SmurfTree::data) weight = lumi*sample.scale1fb_*sample.sfWeightPU_*sample.sfWeightEff_*sample.sfWeightTrig_;    
      
    if (cem == 8 && nsel == 1 && mh == 118) weight *= ((0.472400*0.11800000)/(0.448300*0.14300000));  
    if (cem == 8 && nsel == 1 && mh == 122) weight *= ((0.425700*0.17000000)/(0.448300*0.14300000));  
    if (cem == 8 && nsel == 1 && mh == 124) weight *= ((0.404400*0.200000)/(0.394300*0.216000));    
    if (cem == 8 && nsel == 1 && mh == 126) weight *= ((0.384300*0.233000)/(0.394300*0.216000));   
    if (cem == 8 && nsel == 1 && mh == 128) weight *= ((0.365200*0.26800000)/(0.347300*0.30500000));  
    if (cem == 8 && nsel == 1 && mh == 127.5) weight *= ((0.387300*0.226200)/(0.394300*0.216000)); 
    
    if (cem == 7 && nsel == 1 && mh == 110) weight *= (0.02251917/0.0443547);
    if (cem == 7 && nsel == 1 && mh == 115) weight *= (0.03532622/0.0443547);
    if (cem == 7 && nsel == 1 && mh == 145) weight *= ((0.193000*0.600000)/(0.217200*0.501000));
    if (cem == 7 && nsel == 1 && mh == 125.7) weight *= ((0.215000*0.315800)/(0.226200*0.310100));
    
   
   //Three real leptons MC level
    if (!isData){
      bool isRealLepton = false;
      if((TMath::Abs(sample.lep1McId_) == 11 || TMath::Abs(sample.lep1McId_) == 13) &&
	 (TMath::Abs(sample.lep2McId_) == 11 || TMath::Abs(sample.lep2McId_) == 13) &&
	 (TMath::Abs(sample.lep3McId_) == 11 || TMath::Abs(sample.lep3McId_) == 13)) isRealLepton = true; 
      if (!isRealLepton && !isBackground) continue; //signal
      if (!isRealLepton && sample.dstype_ != SmurfTree::data) continue; //background
    }
																									         
    int ntype = sample.dstype_;
    
    //Check for fakes
    int nFake = 0;
    if(((sample.cuts_ & SmurfTree::Lep1LooseMuV2)  == SmurfTree::Lep1LooseMuV2)  && (sample.cuts_ & SmurfTree::Lep1FullSelection) != SmurfTree::Lep1FullSelection) nFake++;
    if(((sample.cuts_ & SmurfTree::Lep2LooseMuV2)  == SmurfTree::Lep2LooseMuV2)  && (sample.cuts_ & SmurfTree::Lep2FullSelection) != SmurfTree::Lep2FullSelection) nFake++;
    if(((sample.cuts_ & SmurfTree::Lep3LooseMuV2)  == SmurfTree::Lep3LooseMuV2)  && (sample.cuts_ & SmurfTree::Lep3FullSelection) != SmurfTree::Lep3FullSelection) nFake++;
    if(((sample.cuts_ & SmurfTree::Lep1LooseEleV4) == SmurfTree::Lep1LooseEleV4) && (sample.cuts_ & SmurfTree::Lep1FullSelection) != SmurfTree::Lep1FullSelection) nFake++;
    if(((sample.cuts_ & SmurfTree::Lep2LooseEleV4) == SmurfTree::Lep2LooseEleV4) && (sample.cuts_ & SmurfTree::Lep2FullSelection) != SmurfTree::Lep2FullSelection) nFake++;
    if(((sample.cuts_ & SmurfTree::Lep3LooseEleV4) == SmurfTree::Lep3LooseEleV4) && (sample.cuts_ & SmurfTree::Lep3FullSelection) != SmurfTree::Lep3FullSelection) nFake++;
    if (nFake !=0 && !isBackground) continue; 
    if (nFake !=0){ 
      ntype = 61;
      weight*= sample.sfWeightFR_*factor;
      //if (sample.dstype_ != SmurfTree::data) weight *=-1;
    }
    
    
    //2 same flavor, oppposite sign leptons + extra one
    if (sample.lid3_ == sample.lid2_ && sample.lid3_ == sample.lid1_) continue;
    if (sample.lid3_ == sample.lid2_ && fabs(sample.lid3_) != fabs(sample.lid1_)) continue;
    if (sample.lid3_ == sample.lid1_ && fabs(sample.lid3_) != fabs(sample.lid2_)) continue;
    if (sample.lid2_ == sample.lid1_ && fabs(sample.lid2_) != fabs(sample.lid3_)) continue;
    
    // At least 2 jets 
    if (sample.njets_ < 2) continue; 
    if (tau && (sample.jet1McId_ == 100 || sample.jet2McId_ == 100 || sample.jet3McId_ == 100 || sample.jet4McId_ == 100)) continue;

    //Make z-compatible pairs
    double m[3] = {-1, -1, -1};
    LorentzVector pair1, pair2, pair3;
    if (fabs(sample.lid1_) == fabs(sample.lid2_) && sample.lq1_*sample.lq2_ < 0){
      pair1 = sample.lep1_ + sample.lep2_ ;
      m[0] = pair1.M();
      if (m[0] < 12) continue;
    }
    if (fabs(sample.lid2_) == fabs(sample.lid3_) && sample.lq2_*sample.lq3_ < 0){
      pair2 = sample.lep2_ + sample.lep3_ ;
      m[1] = pair2.M();
      if (m[1] < 12) continue;
    }
    if (fabs(sample.lid1_) == fabs(sample.lid3_) && sample.lq1_*sample.lq3_ < 0){
      pair3 = sample.lep1_ + sample.lep3_ ;
      m[2] = pair3.M();
      if (m[2] < 12) continue;
    }
    if ( (m[0] > 0 && m[0] < 12) || (m[1] > 0 && m[1] < 12) || (m[2] > 0 && m[2] < 12)) continue;
    
    LorentzVector trelep = sample.lep1_ + sample.lep2_ + sample.lep3_;
    if (fabs(trelep.M() - mz) < 10) continue; 
																																																	         
    //Get the closest to the Z mass
    double min = TMath::Min(TMath::Min(fabs(mz -m[0]), fabs(mz-m[1])), TMath::Min(fabs(mz -m[0]), fabs(mz-m[2])));
    
    //Select the different things: Z pair, extra lepton, Higgs system
    LorentzVector pair, tlepton, pairjet;
    double mt = 0;
    // double dR = 0; //dR = fabs(ROOT::Math::VectorUtil::DeltaR(sample.lep1_ ,sample.lep2_)) etc
    if (min == fabs(mz - m[0])) {  pair = pair1; mt =  sample.mt3_; tlepton = sample.lep3_;} 
    else if (min == fabs(mz - m[1])){  pair = pair2;  mt =  sample.mt1_; tlepton = sample.lep1_;} 
    else if (min == fabs(mz - m[2])){  pair = pair3;  mt =  sample.mt2_; tlepton = sample.lep2_;} 
    pairjet = sample.jet1_+ sample.jet2_;
    LorentzVector metvector(sample.met_*cos(sample.metPhi_), sample.met_*sin(sample.metPhi_), 0, 0);
    LorentzVector higgsSystem = tlepton + metvector + sample.jet1_+ sample.jet2_;
    LorentzVector lm = tlepton + metvector;
    
    
    double hp[5];
    hp[0] = tlepton.Px() + sample.jet1_.Px()+ sample.jet2_.Px()+ metvector.Px();
    hp[1] = tlepton.Py() + sample.jet1_.Py()+ sample.jet2_.Py()+ metvector.Py();
    hp[2] = tlepton.Pz() + sample.jet1_.Pz()+ sample.jet2_.Pz()+ metvector.Pz();
    
    //Calculate p of the neutrino using Maria's code
    double metp = 0;
    // double otherSol = 0;
    double alpha=(mw*mw-mmu*mmu)/2/tlepton.P()+(tlepton.Px()*sample.met_*cos(sample.metPhi_)+tlepton.Py()*sample.met_*sin(sample.metPhi_))/tlepton.P();
    double A=tlepton.Pz()*tlepton.Pz()/tlepton.P()/tlepton.P()-1;
    double B=2*alpha*tlepton.Pz()/tlepton.P();
    double C=alpha*alpha-(sample.met_*cos(sample.metPhi_)*sample.met_*cos(sample.metPhi_) + sample.met_*sin(sample.metPhi_)*sample.met_*sin(sample.metPhi_));
    // bool isComplex = false;
    double tmproot = B*B - 4.0*A*C;
    if (tmproot<0) { 
      //isComplex= true;
      metp = - B/(2*A); 
      //otherSol = metp;
    } else {
      // isComplex = false;
      double tmpsol1 = (-B + TMath::Sqrt(tmproot))/(2.0*A);
      double tmpsol2 = (-B - TMath::Sqrt(tmproot))/(2.0*A);
      if (TMath::Abs(tmpsol1)<TMath::Abs(tmpsol2) ) {
	metp = tmpsol1; 
	//otherSol = tmpsol2; 
      } else { 
	metp = tmpsol2; 
	//otherSol = tmpsol1; 
      }
    }
    
    
    // hp[3] = tlepton.P() + sample.jet1_.P()+ sample.jet2_.P()+ metvector.P(); //crappy solution
    hp[3] = tlepton.P() + sample.jet1_.P()+ sample.jet2_.P()+ metp;
    hp[4] = tlepton.Pt() + sample.jet1_.Pt()+ sample.jet2_.Pt()+ sample.met_;
    
    double recomh  = hp[3]*hp[3]-hp[0]*hp[0]-hp[1]*hp[1]-hp[2]*hp[2]; if(recomh  > 0) recomh  = sqrt(recomh);else recomh   = 0.0;
    double recomth = hp[4]*hp[4]-hp[0]*hp[0]-hp[1]*hp[1]; if(recomth > 0) recomth = sqrt(recomth); else recomth  = 0.0;
    
    
    //Kinematic cuts
    if (pair.M() < (mz - separation)|| pair.M() > (mz + separation)) continue; 
    if (sample.met_ < metcut) continue;
    if (mt > mtcut) continue;
    if (pairjet.M() < (mw - separationjj) || pairjet.M() > (mw + separationjj)) continue;
    
    //double deltaPhi = fabs(DeltaPhi(pairjet.Phi(),tlepton.Phi()));
    double deltaPhi = fabs(DeltaPhi(pairjet.Phi(),lm.Phi()));
    if (deltaPhi > phicut) continue;
    
    
    if (nsel == 2 && ntype != 49) continue; //WZ
    if (nsel == 3 && ntype != 50) continue; //ZZ
    if (nsel == 4 && ntype != 59) continue; //VVV
    if (nsel == 5 && ntype != 61) continue; //fakes
    if (nsel == 0 && ntype != 0)  continue; //data
    
    
    
      histo->Fill(recomth, weight);
    //histo->Fill(higgsSystem.M(), weight);
    // histo->Fill(1, weight);
    eventsPass+= weight;
    
    
  }    
  
  cout << "[Info:] (" << plotName << ") " <<  eventsPass << " events pass, check " << histo->GetBinContent(1) << endl;
  
  
  f_root.Write();
  f_root.Close();
  
}
Пример #4
0
double ComputeMT(LorentzVector p1, float met, float metphi) {
    double dPhi = deltaPhi(p1.Phi(), metphi);
    // 43.61 of pdg.lbl.gov/2013/reviews/rpp2012-rev-kinematics.pdf
    return sqrt( 2.0 * p1.Pt() * met * (1.0-cos(dPhi)) );
}
Пример #5
0
void doWZ(int cem = 8, int mode = 0){

  char plotName[300];
  sprintf(plotName,"test");
  
  sprintf(plotName,"WZ");
  bool isBackground = true;
  bool isData = false;
  int nsel = 2;
  
  char myRootFile[300];
  if (cem != 7 && cem !=8) cem = 8;
  double lumi = lumi8;
  if (cem == 8){
    sprintf(myRootFile,"/data/smurf/data/Run2012_Summer12_SmurfV9_53X/mitf-alljets/backgroundA_3l.root");
  } else {
    lumi = lumi7;
    sprintf(myRootFile,"/data/smurf/data/Run2011_Fall11_SmurfV9_42X/mitf-alljets/backgroundA_3l.root");
  }
  //Load datasets
  SmurfTree sample;
  sample.LoadTree(myRootFile,-1);
  sample.InitTree(0);

  // Prepare putput file
  char rootFile[300];
  if (cem == 8) sprintf(rootFile,"WZ8TeV.root");
  else sprintf(rootFile,"WZ7TeV.root");

  TFile f_root(rootFile, "RECREATE");
  
  // Prepare histograms
  char title[300];
  
  sprintf(title,"histogram");
  TH1F* histo = new TH1F( title, " ", nbins, nbinlow, nbinhigh);
  histo->Sumw2();

  //Prepare useful things
  double weight = 1;
  double eventsPass = 0;
  
  int nSample=sample.tree_->GetEntries();
   for (int i=0; i<nSample; ++i) {
    
    if (i%100000 == 0 && verboseLevel > 0)
      printf("--- reading event %5d of %5d\n",i,nSample);
    sample.tree_->GetEntry(i);
    
      //Modes, 0 = all, 1 = eee, 2 = eem, 3 = emm, 4 = mmm
    if (mode == 1 && (abs(sample.lid1_)!= 11 || abs(sample.lid2_) != 11 || abs(sample.lid3_) != 11)) continue;
    if (mode == 2 && 
       ((abs(sample.lid1_)!= abs(sample.lid2_) && abs(sample.lid1_) != abs(sample.lid3_) && abs(sample.lid1_) == 11) ||
        (abs(sample.lid2_)!= abs(sample.lid1_) && abs(sample.lid2_) != abs(sample.lid3_) && abs(sample.lid2_) == 11) ||
	(abs(sample.lid3_)!= abs(sample.lid1_) && abs(sample.lid3_) != abs(sample.lid2_) && abs(sample.lid3_) == 11) ||
	(abs(sample.lid1_) == abs(sample.lid2_) && abs(sample.lid1_) == abs(sample.lid3_)))) continue;
    if (mode == 3 && 
       ((abs(sample.lid1_)!= abs(sample.lid2_) && abs(sample.lid1_) != abs(sample.lid3_) && abs(sample.lid1_) == 13) ||
        (abs(sample.lid2_)!= abs(sample.lid1_) && abs(sample.lid2_) != abs(sample.lid3_) && abs(sample.lid2_) == 13) ||
	(abs(sample.lid3_)!= abs(sample.lid1_) && abs(sample.lid3_) != abs(sample.lid2_) && abs(sample.lid3_) == 13) ||
	(abs(sample.lid1_) == abs(sample.lid2_) && abs(sample.lid1_) == abs(sample.lid3_)))) continue;
    if (mode == 4 && (abs(sample.lid1_)!= 13 || abs(sample.lid2_) != 13 || abs(sample.lid3_) != 13)) continue;
   

    
    weight = 1;
    if (!isData && sample.dstype_ != SmurfTree::data) weight = lumi*sample.scale1fb_*sample.sfWeightPU_*sample.sfWeightEff_*sample.sfWeightTrig_;    
   
   //Three real leptons MC level
    if (!isData){
      bool isRealLepton = false;
      if((TMath::Abs(sample.lep1McId_) == 11 || TMath::Abs(sample.lep1McId_) == 13) &&
         (TMath::Abs(sample.lep2McId_) == 11 || TMath::Abs(sample.lep2McId_) == 13) &&
         (TMath::Abs(sample.lep3McId_) == 11 || TMath::Abs(sample.lep3McId_) == 13)) isRealLepton = true; 
      if (!isRealLepton && !isBackground) continue; //signal
      if (!isRealLepton && sample.dstype_ != SmurfTree::data) continue; //background
    }
    
    int ntype = sample.dstype_;
    
     //Check for fakes
    int nFake = 0;
    if(((sample.cuts_ & SmurfTree::Lep1LooseMuV2)  == SmurfTree::Lep1LooseMuV2)  && (sample.cuts_ & SmurfTree::Lep1FullSelection) != SmurfTree::Lep1FullSelection) nFake++;
    if(((sample.cuts_ & SmurfTree::Lep2LooseMuV2)  == SmurfTree::Lep2LooseMuV2)  && (sample.cuts_ & SmurfTree::Lep2FullSelection) != SmurfTree::Lep2FullSelection) nFake++;
    if(((sample.cuts_ & SmurfTree::Lep3LooseMuV2)  == SmurfTree::Lep3LooseMuV2)  && (sample.cuts_ & SmurfTree::Lep3FullSelection) != SmurfTree::Lep3FullSelection) nFake++;
    if(((sample.cuts_ & SmurfTree::Lep1LooseEleV4) == SmurfTree::Lep1LooseEleV4) && (sample.cuts_ & SmurfTree::Lep1FullSelection) != SmurfTree::Lep1FullSelection) nFake++;
    if(((sample.cuts_ & SmurfTree::Lep2LooseEleV4) == SmurfTree::Lep2LooseEleV4) && (sample.cuts_ & SmurfTree::Lep2FullSelection) != SmurfTree::Lep2FullSelection) nFake++;
    if(((sample.cuts_ & SmurfTree::Lep3LooseEleV4) == SmurfTree::Lep3LooseEleV4) && (sample.cuts_ & SmurfTree::Lep3FullSelection) != SmurfTree::Lep3FullSelection) nFake++;
    if (nFake !=0 && !isBackground) continue; 
    if (nFake !=0){ 
      ntype = 61;
      weight*= sample.sfWeightFR_*factor;
      //if (sample.dstype_ != SmurfTree::data) weight *=-1;
    }
    
    if (nsel == 2 && ntype != 49) continue; //WZ
    
    //2 same flavor, oppposite sign leptons + extra one
    if (sample.lid3_ == sample.lid2_ && sample.lid3_ == sample.lid1_) continue;
    if (sample.lid3_ == sample.lid2_ && fabs(sample.lid3_) != fabs(sample.lid1_)) continue;
    if (sample.lid3_ == sample.lid1_ && fabs(sample.lid3_) != fabs(sample.lid2_)) continue;
    if (sample.lid2_ == sample.lid1_ && fabs(sample.lid2_) != fabs(sample.lid3_)) continue;
    
    // At least 2 jets 
    if (sample.njets_ < 2) continue; 
    if (tau && (sample.jet1McId_ == 100 || sample.jet2McId_ == 100 || sample.jet3McId_ == 100 || sample.jet4McId_ == 100)) continue;

       //Make z-compatible pairs
    double m[3] = {-1, -1, -1};
    LorentzVector pair1, pair2, pair3;
    if (fabs(sample.lid1_) == fabs(sample.lid2_) && sample.lq1_*sample.lq2_ < 0){
      pair1 = sample.lep1_ + sample.lep2_ ;
      m[0] = pair1.M();
      if (m[0] < 12) continue;
    }
    if (fabs(sample.lid2_) == fabs(sample.lid3_) && sample.lq2_*sample.lq3_ < 0){
      pair2 = sample.lep2_ + sample.lep3_ ;
      m[1] = pair2.M();
      if (m[1] < 12) continue;
    }
    if (fabs(sample.lid1_) == fabs(sample.lid3_) && sample.lq1_*sample.lq3_ < 0){
      pair3 = sample.lep1_ + sample.lep3_ ;
      m[2] = pair3.M();
      if (m[2] < 12) continue;
    }
    if ( (m[0] > 0 && m[0] < 12) || (m[1] > 0 && m[1] < 12) || (m[2] > 0 && m[2] < 12)) continue;
    				
   LorentzVector trelep = sample.lep1_ + sample.lep2_ + sample.lep3_;
   if (fabs(trelep.M() - mz) < 10) continue; 
						
    //Get the closest to the Z mass
    double min = TMath::Min(TMath::Min(fabs(mz -m[0]), fabs(mz-m[1])), TMath::Min(fabs(mz -m[0]), fabs(mz-m[2])));
   
    //Select the different things: Z pair, extra lepton, Higgs system
    LorentzVector pair, tlepton, pairjet;
    double mt = 0;
   // double dR = 0; //dR = fabs(ROOT::Math::VectorUtil::DeltaR(sample.lep1_ ,sample.lep2_)) etc
    if (min == fabs(mz - m[0])) {  pair = pair1; mt =  sample.mt3_; tlepton = sample.lep3_;} 
    else if (min == fabs(mz - m[1])){  pair = pair2;  mt =  sample.mt1_; tlepton = sample.lep1_;} 
    else if (min == fabs(mz - m[2])){  pair = pair3;  mt =  sample.mt2_; tlepton = sample.lep2_;} 
    pairjet = sample.jet1_+ sample.jet2_;
    LorentzVector metvector(sample.met_*cos(sample.metPhi_), sample.met_*sin(sample.metPhi_), 0, 0);
    LorentzVector higgsSystem = tlepton + metvector + sample.jet1_+ sample.jet2_;
    LorentzVector lm = tlepton + metvector;
   
      
    double hp[5];
    hp[0] = tlepton.Px() + sample.jet1_.Px()+ sample.jet2_.Px()+ metvector.Px();
    hp[1] = tlepton.Py() + sample.jet1_.Py()+ sample.jet2_.Py()+ metvector.Py();
    hp[2] = tlepton.Pz() + sample.jet1_.Pz()+ sample.jet2_.Pz()+ metvector.Pz();
    
    //Calculate p of the neutrino using Maria's code
    double metp = 0;
   // double otherSol = 0;
    double alpha=(mw*mw-mmu*mmu)/2/tlepton.P()+(tlepton.Px()*sample.met_*cos(sample.metPhi_)+tlepton.Py()*sample.met_*sin(sample.metPhi_))/tlepton.P();
    double A=tlepton.Pz()*tlepton.Pz()/tlepton.P()/tlepton.P()-1;
    double B=2*alpha*tlepton.Pz()/tlepton.P();
    double C=alpha*alpha-(sample.met_*cos(sample.metPhi_)*sample.met_*cos(sample.metPhi_) + sample.met_*sin(sample.metPhi_)*sample.met_*sin(sample.metPhi_));
   // bool isComplex = false;
    double tmproot = B*B - 4.0*A*C;
      if (tmproot<0) { 
        //isComplex= true;
        metp = - B/(2*A); 
	//otherSol = metp;
      } else {
       // isComplex = false;
	double tmpsol1 = (-B + TMath::Sqrt(tmproot))/(2.0*A);
	double tmpsol2 = (-B - TMath::Sqrt(tmproot))/(2.0*A);
	if (TMath::Abs(tmpsol1)<TMath::Abs(tmpsol2) ) {
	  metp = tmpsol1; 
	  //otherSol = tmpsol2; 
	} else { 
	  metp = tmpsol2; 
	  //otherSol = tmpsol1; 
	}
     }
   
    
   // hp[3] = tlepton.P() + sample.jet1_.P()+ sample.jet2_.P()+ metvector.P(); //crappy solution
    hp[3] = tlepton.P() + sample.jet1_.P()+ sample.jet2_.P()+ metp;
    hp[4] = tlepton.Pt() + sample.jet1_.Pt()+ sample.jet2_.Pt()+ sample.met_;
    
    double recomh  = hp[3]*hp[3]-hp[0]*hp[0]-hp[1]*hp[1]-hp[2]*hp[2]; if(recomh  > 0) recomh  = sqrt(recomh);else recomh   = 0.0;
    double recomth = hp[4]*hp[4]-hp[0]*hp[0]-hp[1]*hp[1]; if(recomth > 0) recomth = sqrt(recomth); else recomth  = 0.0;
    
   
    //Kinematic cuts
    if (pair.M() < (mz - separation)|| pair.M() > (mz + separation)) continue; 
    if (sample.met_ < metcut) continue;
    if (mt > mtcut) continue;
    if (pairjet.M() < (mw - separationjj) || pairjet.M() > (mw + separationjj)) continue;
    
   //double deltaPhi = fabs(DeltaPhi(pairjet.Phi(),tlepton.Phi()));
    double deltaPhi = fabs(DeltaPhi(pairjet.Phi(),lm.Phi()));
    if (deltaPhi > phicut) continue;
   
    
    histo->Fill(recomth, weight);
    //histo->Fill(higgsSystem.M(), weight);
    eventsPass+= weight;
     
  
  }    
  
   cout << "[Info:] (" << plotName << ") " <<  eventsPass << " events pass " << endl;
  
  
    f_root.Write();
    f_root.Close();
 
}
Пример #6
0
float dRbetweenVectors(LorentzVector& vec1,LorentzVector& vec2 ){                                                                                                              
  float dphi = std::min(::fabs(vec1.Phi() - vec2.Phi()), 2 * M_PI - fabs(vec1.Phi() - vec2.Phi()));
  float deta = vec1.Eta() - vec2.Eta();

  return sqrt(dphi*dphi + deta*deta);
}
Пример #7
0
int ScanChain( TChain* chain, bool fast = true, int nEvents = -1, string skimFilePrefix = "test") {

  int currentrun = -1;
  bool DCSonly = false;//KEEP THIS FALSE
  // Benchmark
  TBenchmark *bmark = new TBenchmark();
  bmark->Start("benchmark");

  // Example Histograms
  TDirectory *rootdir = gDirectory->GetDirectory("Rint:");

  map<string, TH1F*> histos;
  vector<string> histonames; histonames.clear();
  vector<int> hbins; hbins.clear();
  vector<float> hlow; hlow.clear();
  vector<float> hup; hup.clear();
  histonames.push_back("Mll");                       hbins.push_back(75); hlow.push_back(  15.); hup.push_back(390);
  histonames.push_back("Mud0");                      hbins.push_back(40); hlow.push_back( -0.4); hup.push_back(0.4);
  histonames.push_back("MudZ");                      hbins.push_back(40); hlow.push_back(  -1.); hup.push_back(1. );
  histonames.push_back("MuIP3d");                    hbins.push_back(40); hlow.push_back( -0.5); hup.push_back(0.5);
  histonames.push_back("MuRelIso03");                hbins.push_back(50); hlow.push_back(   0.); hup.push_back(2. );
  histonames.push_back("MuRelIso03EA");              hbins.push_back(50); hlow.push_back(   0.); hup.push_back(2. );
  histonames.push_back("MuRelIso03DB");              hbins.push_back(50); hlow.push_back(   0.); hup.push_back(2. );
  histonames.push_back("MuMiniIsoEA");               hbins.push_back(50); hlow.push_back(   0.); hup.push_back(2. );
  histonames.push_back("MuMiniIsoDB");               hbins.push_back(50); hlow.push_back(   0.); hup.push_back(2. );
  histonames.push_back("MuRelIso04");                hbins.push_back(50); hlow.push_back(   0.); hup.push_back(2. );
  histonames.push_back("MuAnnulus04");               hbins.push_back(25); hlow.push_back(   0.); hup.push_back(1. );
  histonames.push_back("MuRelIso03_MT30");           hbins.push_back(50); hlow.push_back(   0.); hup.push_back(2. );
  histonames.push_back("MuRelIso03EA_MT30");         hbins.push_back(50); hlow.push_back(   0.); hup.push_back(2. );
  histonames.push_back("MuRelIso03DB_MT30");         hbins.push_back(50); hlow.push_back(   0.); hup.push_back(2. );
  histonames.push_back("MuMiniIsoEA_MT30");          hbins.push_back(50); hlow.push_back(   0.); hup.push_back(2. );
  histonames.push_back("MuMiniIsoDB_MT30");          hbins.push_back(50); hlow.push_back(   0.); hup.push_back(2. );
  histonames.push_back("MuRelIso04_MT30");           hbins.push_back(50); hlow.push_back(   0.); hup.push_back(2. );
  histonames.push_back("MuAnnulus04_MT30");          hbins.push_back(25); hlow.push_back(   0.); hup.push_back(1. );
  histonames.push_back("MuID");                      hbins.push_back( 7); hlow.push_back(  -1.); hup.push_back(6. );
  histonames.push_back("MuvalidFraction");           hbins.push_back(25); hlow.push_back(   0.); hup.push_back(1. );
  histonames.push_back("MuisPF");                    hbins.push_back( 5); hlow.push_back(  -1.); hup.push_back(4. );
  histonames.push_back("Mugfit_normchi2");           hbins.push_back(40); hlow.push_back(   0.); hup.push_back(20.);
  histonames.push_back("Mugfit_validSTAHits");       hbins.push_back(10); hlow.push_back(   0.); hup.push_back(10.);
  histonames.push_back("MunumberOfMatchedStations"); hbins.push_back(10); hlow.push_back(   0.); hup.push_back(10.);
  histonames.push_back("Munlayers");                 hbins.push_back(20); hlow.push_back(   0.); hup.push_back(20.);
  histonames.push_back("Muchi2LocalPosition");       hbins.push_back(40); hlow.push_back(   0.); hup.push_back(40.);
  histonames.push_back("MutrkKink");                 hbins.push_back(50); hlow.push_back(   0.); hup.push_back(50.);
  histonames.push_back("MusegmCompatibility");       hbins.push_back(35); hlow.push_back(   0.); hup.push_back(1.4);
  histonames.push_back("MuvalidPixelHits");          hbins.push_back( 5); hlow.push_back(   0.); hup.push_back(5. );
  histonames.push_back("MuPt");                      hbins.push_back(30); hlow.push_back(   0.); hup.push_back(600);
  histonames.push_back("MuEta");                     hbins.push_back(60); hlow.push_back(   3.); hup.push_back(3. );
  histonames.push_back("MuPhi");                     hbins.push_back(32); hlow.push_back( -3.2); hup.push_back(3.2);
  histonames.push_back("MuCharge");                  hbins.push_back( 6); hlow.push_back(  -2.); hup.push_back(4. );
  histonames.push_back("MT");                        hbins.push_back(45); hlow.push_back(   0.); hup.push_back(450);
  histonames.push_back("ZPt");                       hbins.push_back(30); hlow.push_back(   0.); hup.push_back(600);
  histonames.push_back("Z_Pt");                      hbins.push_back(30); hlow.push_back(   0.); hup.push_back(600);
  histonames.push_back("ZEta");                      hbins.push_back(50); hlow.push_back(  -5.); hup.push_back(5. );
  histonames.push_back("ZPhi");                      hbins.push_back(32); hlow.push_back( -3.2); hup.push_back(3.2);
  histonames.push_back("DPhill");                    hbins.push_back(32); hlow.push_back(   0.); hup.push_back(3.2);
  histonames.push_back("DEtall");                    hbins.push_back(50); hlow.push_back(   0.); hup.push_back(5. );
  histonames.push_back("DRll");                      hbins.push_back(32); hlow.push_back(   0.); hup.push_back(6.4);
  histonames.push_back("MyMuPt");                      hbins.push_back(30); hlow.push_back(   0.); hup.push_back(600);
  histonames.push_back("MyMuEta");                     hbins.push_back(60); hlow.push_back(   3.); hup.push_back(3. );
  histonames.push_back("MyMuPhi");                     hbins.push_back(32); hlow.push_back( -3.2); hup.push_back(3.2);
  histonames.push_back("MyMuCharge");                  hbins.push_back( 6); hlow.push_back(  -2.); hup.push_back(4. );
  histonames.push_back("MET");                      hbins.push_back(40); hlow.push_back(   0.); hup.push_back(200);
  histonames.push_back("HT");                      hbins.push_back(40); hlow.push_back(   0.); hup.push_back(400);
  histonames.push_back("NJets");                      hbins.push_back(10); hlow.push_back(   0.); hup.push_back(10);
  histonames.push_back("NBJets");                      hbins.push_back(5); hlow.push_back(   0.); hup.push_back(5);
	      
  for(unsigned int i = 0; i<histonames.size(); ++i){
    int nbins = hbins[i];
    string mapname;
    for(unsigned int j = 0; j<11; ++j){
      string prefix = "";
      if(j==1) prefix = "NJ0_";
      else if(j==2) prefix = "NJ1_";
      else if(j==3) prefix = "NJ2_";
      else if(j==4) prefix = "NJge3_";
      else if(j==5) prefix = "NB0_";
      else if(j==6) prefix = "NBge1_";
      else if(j==7) prefix = "HTge100_";
      else if(j==8) prefix = "METge50_";
      else if(j==9) prefix = "METge25_";
      else if(j==10) prefix = "HTge150_";
      mapname = prefix + histonames[i]+"_"+skimFilePrefix;
      //cout << mapname << endl;
      if(histos.count(mapname) == 0 ) histos[mapname] = new TH1F(mapname.c_str(), "", nbins, hlow[i], hup[i]);
      histos[mapname]->Sumw2(); histos[mapname]->SetDirectory(rootdir);
    }
  }

  // Loop over events to Analyze
  unsigned int nEventsTotal = 0;
  unsigned int nEventsChain = chain->GetEntries();
  if( nEvents >= 0 ) nEventsChain = nEvents;
  TObjArray *listOfFiles = chain->GetListOfFiles();
  TIter fileIter(listOfFiles);
  TFile *currentFile = 0;

  //load json file
  const char* json_fileDCS = "myjsons/json_DCSONLY_Run2015B_snt.txt";
  const char* json_file = "myjsons/json_Golden_246908-251883_snt.txt";
  if(DCSonly) set_goodrun_file(json_fileDCS);
  else        set_goodrun_file(json_file);

  // File Loop
  while ( (currentFile = (TFile*)fileIter.Next()) ) {

    // Get File Content
    TFile *file = new TFile( currentFile->GetTitle() );
    TTree *tree = (TTree*)file->Get("t");
    if(fast) TTreeCache::SetLearnEntries(10);
    if(fast) tree->SetCacheSize(128*1024*1024);
    cms3.Init(tree);

    int nleps = 1;
    myevt p;//previous event
    myevt c;//current event
    resetEvent(p);
    resetEvent(c);
    vector<myevt> mu; mu.clear();

    // Loop over Events in current file
    if( nEventsTotal >= nEventsChain ) continue;
    unsigned int nEventsTree = tree->GetEntriesFast();
    for( unsigned int event = 0; event < nEventsTree; ++event) {
    
      // Get Event Content
      if( nEventsTotal >= nEventsChain ) continue;
      if(fast) tree->LoadTree(event);
      cms3.GetEntry(event);
      ++nEventsTotal;
    
      // Progress
      CMS3::progress(nEventsTotal, nEventsChain );
      if(evt_isRealData()&& !goodrun(evt_run(), evt_lumiBlock()) ) continue;

      //load my struct
      c.evt_pfmet   = evt_pfmet();
      c.evt_pfmetPhi   = evt_pfmetPhi();
      c.evt_trackmet   = evt_trackmet();
      c.evt_trackmetPhi   = evt_trackmetPhi();
      c.evt_pfsumet   = evt_pfsumet();
      c.evt_pfmetSig   = evt_pfmetSig();
      c.evt_event   = evt_event();
      c.evt_lumiBlock   = evt_lumiBlock();
      c.evt_run   = evt_run();
      c.filt_csc   = filt_csc();
      c.filt_hbhe   = filt_hbhe();
      c.filt_hcallaser   = filt_hcallaser();
      c.filt_ecaltp   = filt_ecaltp();
      c.filt_trkfail   = filt_trkfail();
      c.filt_eebadsc   = filt_eebadsc();
      c.evt_isRealData   = evt_isRealData(); 
      c.scale1fb   = scale1fb();
      c.evt_xsec_incl   = evt_xsec_incl();
      c.evt_kfactor   = evt_kfactor();
      c.gen_met   = gen_met();
      c.gen_metPhi   = gen_metPhi();
      c.njets   = njets();
      c.ht   = ht();
      c.jets  = jets();
      c.jets_disc  = jets_disc();
      c.sample  = sample();
      c.nvtx   = nvtx();
      c.HLT_Mu8_TrkIsoVVL   = HLT_Mu8_TrkIsoVVL();
      c.HLT_Mu17_TrkIsoVVL   = HLT_Mu17_TrkIsoVVL();
      c.HLT_Mu24_TrkIsoVVL   = HLT_Mu24_TrkIsoVVL();
      c.HLT_Mu34_TrkIsoVVL   = HLT_Mu34_TrkIsoVVL();
      c.HLT_Mu8   = HLT_Mu8();
      c.HLT_Mu17   = HLT_Mu17();
      c.HLT_Mu24   = HLT_Mu24();
      c.HLT_Mu34   = HLT_Mu34();
      c.HLT_Mu10_CentralPFJet30_BTagCSV0p5PF   = HLT_Mu10_CentralPFJet30_BTagCSV0p5PF();
      c.HLT_IsoMu24_eta2p1   = HLT_IsoMu24_eta2p1();
      c.HLT_IsoTkMu24_eta2p1   = HLT_IsoTkMu24_eta2p1(); 
      c.HLT_IsoMu27   = HLT_IsoMu27();
      c.HLT_IsoTkMu27   = HLT_IsoTkMu27(); 
      c.HLT_Mu45_eta2p1   = HLT_Mu45_eta2p1(); 
      c.HLT_Mu50   = HLT_Mu50();
      c.HLT_Ele8_CaloIdM_TrackIdM_PFJet30   = HLT_Ele8_CaloIdM_TrackIdM_PFJet30();
      c.HLT_Ele12_CaloIdM_TrackIdM_PFJet30   = HLT_Ele12_CaloIdM_TrackIdM_PFJet30();
      c.HLT_Ele18_CaloIdM_TrackIdM_PFJet30   = HLT_Ele18_CaloIdM_TrackIdM_PFJet30();
      c.HLT_Ele23_CaloIdM_TrackIdM_PFJet30   = HLT_Ele23_CaloIdM_TrackIdM_PFJet30();
      c.HLT_Ele33_CaloIdM_TrackIdM_PFJet30   = HLT_Ele33_CaloIdM_TrackIdM_PFJet30();
      c.HLT_Ele12_CaloIdL_TrackIdL_IsoVL_PFJet30   = HLT_Ele12_CaloIdL_TrackIdL_IsoVL_PFJet30();
      c.HLT_Ele18_CaloIdL_TrackIdL_IsoVL_PFJet30   = HLT_Ele18_CaloIdL_TrackIdL_IsoVL_PFJet30();
      c.HLT_Ele23_CaloIdL_TrackIdL_IsoVL_PFJet30   = HLT_Ele23_CaloIdL_TrackIdL_IsoVL_PFJet30();
      c.HLT_Ele33_CaloIdL_TrackIdL_IsoVL_PFJet30   = HLT_Ele33_CaloIdL_TrackIdL_IsoVL_PFJet30();
      c.HLT_Ele10_CaloIdM_TrackIdM_CentralPFJet30_BTagCSV0p5PF   = HLT_Ele10_CaloIdM_TrackIdM_CentralPFJet30_BTagCSV0p5PF();
      c.HLT_Ele27_eta2p1_WP75_Gsf   = HLT_Ele27_eta2p1_WP75_Gsf();
      c.HLT_Ele27_WP85_Gsf   = HLT_Ele27_WP85_Gsf();
      c.HLT_Ele27_eta2p1_WPLoose_Gsf   = HLT_Ele27_eta2p1_WPLoose_Gsf();
      c.HLT_Ele27_eta2p1_WPTight_Gsf   = HLT_Ele27_eta2p1_WPTight_Gsf();
      c.HLT_Ele32_eta2p1_WP75_Gsf   = HLT_Ele32_eta2p1_WP75_Gsf();
      c.HLT_Ele32_eta2p1_WPLoose_Gsf   = HLT_Ele32_eta2p1_WPLoose_Gsf();
      c.HLT_Ele32_eta2p1_WPTight_Gsf   = HLT_Ele32_eta2p1_WPTight_Gsf();
      c.HLT_Mu8_Ele8_CaloIdM_TrackIdM_Mass8_PFHT300   = HLT_Mu8_Ele8_CaloIdM_TrackIdM_Mass8_PFHT300();
      c.HLT_Mu23_TrkIsoVVL_Ele12_CaloIdL_TrackIdL_IsoVL   = HLT_Mu23_TrkIsoVVL_Ele12_CaloIdL_TrackIdL_IsoVL();
      c.HLT_Mu8_TrkIsoVVL_Ele23_CaloIdL_TrackIdL_IsoVL   = HLT_Mu8_TrkIsoVVL_Ele23_CaloIdL_TrackIdL_IsoVL();
      c.HLT_DoubleMu8_Mass8_PFHT300   = HLT_DoubleMu8_Mass8_PFHT300();
      c.HLT_Mu17_TrkIsoVVL_Mu8_TrkIsoVVL   = HLT_Mu17_TrkIsoVVL_Mu8_TrkIsoVVL();
      c.HLT_Mu17_TrkIsoVVL_TkMu8_TrkIsoVVL   = HLT_Mu17_TrkIsoVVL_TkMu8_TrkIsoVVL(); 
      c.HLT_Mu17_TrkIsoVVL_Mu8_TrkIsoVVL_DZ   = HLT_Mu17_TrkIsoVVL_Mu8_TrkIsoVVL_DZ();
      c.HLT_Mu17_TrkIsoVVL_TkMu8_TrkIsoVVL_DZ   = HLT_Mu17_TrkIsoVVL_TkMu8_TrkIsoVVL_DZ(); 
      c.HLT_DoubleEle8_CaloIdM_TrackIdM_Mass8_PFHT300   = HLT_DoubleEle8_CaloIdM_TrackIdM_Mass8_PFHT300();
      c.HLT_Ele23_Ele12_CaloIdL_TrackIdL_IsoVL_DZ   = HLT_Ele23_Ele12_CaloIdL_TrackIdL_IsoVL_DZ();
      c.pid_PFMuon   = pid_PFMuon();
      c.gfit_chi2   = gfit_chi2();
      c.gfit_ndof   = gfit_ndof();
      c.gfit_validSTAHits   = gfit_validSTAHits();
      c.numberOfMatchedStations   = numberOfMatchedStations();
      c.validPixelHits   = validPixelHits();
      c.nlayers   = nlayers();
      c.chi2LocalPosition   = chi2LocalPosition();
      c.trkKink   = trkKink();
      c.validHits   = validHits(); 
      c.lostHits   = lostHits();
      c.exp_outerlayers   = exp_outerlayers();
      c.segmCompatibility   = segmCompatibility();
      c.exp_innerlayers   = exp_innerlayers();
      c.passes_POG_vetoID   = passes_POG_vetoID();
      c.passes_POG_looseID   = passes_POG_looseID();
      c.passes_POG_mediumID   = passes_POG_mediumID();
      c.passes_POG_tightID   = passes_POG_tightID();
      c.ip3d   = ip3d();
      c.ip3derr   = ip3derr(); 
      c.type   = type();
      c.mt   = mt();
      c.ptrelv0   = ptrelv0();
      c.ptrelv1   = ptrelv1();
      c.miniiso   = miniiso();
      c.miniisoDB   = miniisoDB(); 
      c.reliso04   = reliso04();
      c.annulus04   = annulus04();
      c.p4  = p4();
      c.tag_p4  = tag_p4();
      c.dilep_p4  = dilep_p4();
      c.mc_p4  = mc_p4();
      c.mc_motherp4  = mc_motherp4();
      c.id   = id();
      c.idx   = idx();
      c.dxyPV   = dxyPV();
      c.dZ   = dZ();
      c.dxyPV_err   = dxyPV_err();
      c.motherID   = motherID();
      c.mc_id   = mc_id();
      c.RelIso03   = RelIso03();
      c.RelIso03EA   = RelIso03EA();
      c.RelIso03DB   = RelIso03DB();
      c.dilep_mass   = dilep_mass();
      c.dilep_p4   = dilep_p4();
      c.passes_SS_tight_noiso_v3 = passes_SS_tight_noiso_v3();
      c.passes_SS_fo_noiso_v3 = passes_SS_fo_noiso_v3();
      c.passes_POG_looseID = passLooseID(c);
      c.passes_POG_mediumID = passMediumID(c);
      c.passes_POG_tightID = passTightID(c);
     

      float weight = p.scale1fb*0.0403;
      if(skimFilePrefix=="DY_M10_50ns") weight *= 1.11;
      if(p.evt_isRealData) weight = 1.;
      if((skimFilePrefix=="SingleMuon"||skimFilePrefix=="DoubleMuon")&&fabs(weight-1.)>=0.001) cout <<__LINE__<< endl;
      // Analysis Code

      if(sameEvent(p,c)) { ++nleps; }


      if(((!sameEvent(p,c))||(nEventsChain==nEventsTotal)) && mu.size()>0) {

	int nbs = 0;
	int njs = 0;
	float HT = 0;
	double muovind[mu.size()];
	for(unsigned int i = 0; i<mu.size();++i){
	  muovind[i] = -1;
	  float minDR = 9999;
	  if(mu[i].jets.size()!=p.jets.size()) cout << "ERROR " << mu[i].jets.size() << " " << p.jets.size() << endl;
	  for(unsigned int j = 0; j<p.jets.size();++j){
	    float myDR = deltaR(mu[i].p4,p.jets[j]);
	    if(myDR<0.4 && myDR<minDR){
	      minDR = myDR;
	      muovind[i] = j;
	    }
	  }
	}
	for(unsigned int i = 0; i<p.jets.size();++i){
	  bool isoverlap = false;
	  for(unsigned int j = 0; j<mu.size();++j){
	    if(muovind[j]==i){
	      isoverlap = true;
	      break;
	    }
	  }
	  if(isoverlap) continue;
	  if(p.jets[i].Pt()<30) continue;
	  if(fabs(p.jets[i].Eta()>2.4)) continue;
	  ++njs;
	  HT += p.jets[i].Pt();
	  if(p.jets_disc[i]>0.890) ++nbs;
	}
      
	bool triggerbool2mu = false;
	bool triggerbool1mu = false;
	//now I reached full event!
	if(mu.size()>1) mu = sortbypt(mu);
	for(unsigned int i = 0; i<mu.size();++i){
	  if(mu[i].evt_isRealData) triggerbool2mu = triggerbool2mu || mu[i].HLT_Mu17_TrkIsoVVL_Mu8_TrkIsoVVL_DZ || mu[i].HLT_Mu17_TrkIsoVVL_TkMu8_TrkIsoVVL_DZ;
	  if(mu[i].evt_isRealData) triggerbool1mu = triggerbool1mu || mu[i].HLT_IsoMu24_eta2p1 || mu[i].HLT_IsoTkMu24_eta2p1 || mu[i].HLT_IsoMu27 || mu[i].HLT_IsoTkMu27 || mu[i].HLT_IsoMu20 || mu[i].HLT_IsoMu20;
	}
	if(!p.evt_isRealData){ triggerbool2mu = true; triggerbool1mu = true;}
	if(mu.size()==2){
	  triggerbool2mu = triggerbool2mu&&mu[0].p4.Pt()>20.&&fabs(mu[0].p4.Eta())<2.1&&mu[0].p4.Pt()>20.&&fabs(mu[0].p4.Eta())<2.1;//two muons passing nominal trigger w/o iso and dZ
	  triggerbool1mu = triggerbool1mu&&((mu[0].p4.Pt()>30.&&fabs(mu[0].p4.Eta())<2.1)||(mu[1].p4.Pt()>30.&&fabs(mu[1].p4.Eta())<2.1));//one muon passing nominal trigger w/o iso
	  LorentzVector Z = (mu[0].p4+mu[1].p4);
	  if((triggerbool1mu||triggerbool2mu)&& mu[0].passes_POG_tightID&&mu[1].passes_POG_tightID&&mu[0].miniisoDB<0.2&&mu[1].miniisoDB<0.2&&
	      fabs(mu[0].dZ)<0.1&&fabs(mu[1].dZ)<0.1&&fabs(mu[0].dxyPV)<0.02&&fabs(mu[1].dxyPV)<0.02){
	    //cout << "have a dilepton event: Z pt " << Z.Pt() << " and mass " << Z.M() << endl;
	    histos["Mll_"+skimFilePrefix]->Fill(Z.M(),weight);
	    if(njs==0) histos["NJ0_Mll_"+skimFilePrefix]->Fill(Z.M(),weight);
	    else if(njs==1) histos["NJ1_Mll_"+skimFilePrefix]->Fill(Z.M(),weight);
	    else if(njs==2) histos["NJ2_Mll_"+skimFilePrefix]->Fill(Z.M(),weight);
	    else histos["NJge3_Mll_"+skimFilePrefix]->Fill(Z.M(),weight);
	    if(nbs==0)  histos["NB0_Mll_"+skimFilePrefix]->Fill(Z.M(),weight);
	    else  histos["NBge1_Mll_"+skimFilePrefix]->Fill(Z.M(),weight);
	    if(HT>100.) histos["HTge100_Mll_"+skimFilePrefix]->Fill(Z.M(),weight);
	    if(HT>150.) histos["HTge150_Mll_"+skimFilePrefix]->Fill(Z.M(),weight);
	    if(p.evt_pfmet>50.) histos["METge50_Mll_"+skimFilePrefix]->Fill(Z.M(),weight);
	    if(p.evt_pfmet>25.) histos["METge25_Mll_"+skimFilePrefix]->Fill(Z.M(),weight);
	    if(Z.M()>75.&&Z.M()<105){
	      histos["ZPt_"+skimFilePrefix]->Fill(Z.Pt(),weight);
	      histos["ZEta_"+skimFilePrefix]->Fill(Z.Eta(),weight);
	      histos["ZPhi_"+skimFilePrefix]->Fill(Z.Phi(),weight);
	      histos["DPhill_"+skimFilePrefix]->Fill(getdphi(mu[0].p4.Phi(),mu[1].p4.Phi()),weight);
	      histos["DEtall_"+skimFilePrefix]->Fill(fabs(mu[0].p4.Eta()-mu[1].p4.Eta()),weight);
	      histos["DRll_"+skimFilePrefix]->Fill(dRbetweenVectors(mu[0].p4,mu[1].p4),weight);
	      histos["MET_"+skimFilePrefix]->Fill(p.evt_pfmet,weight);
	      histos["HT_"+skimFilePrefix]->Fill(HT,weight);
	      histos["NJets_"+skimFilePrefix]->Fill(njs,weight);
	      histos["NBJets_"+skimFilePrefix]->Fill(nbs,weight);
	      if(njs==0){
		histos["NJ0_ZPt_"+skimFilePrefix]->Fill(Z.Pt(),weight);
		histos["NJ0_ZEta_"+skimFilePrefix]->Fill(Z.Eta(),weight);
		histos["NJ0_ZPhi_"+skimFilePrefix]->Fill(Z.Phi(),weight);
		histos["NJ0_DPhill_"+skimFilePrefix]->Fill(getdphi(mu[0].p4.Phi(),mu[1].p4.Phi()),weight);
		histos["NJ0_DEtall_"+skimFilePrefix]->Fill(fabs(mu[0].p4.Eta()-mu[1].p4.Eta()),weight);
		histos["NJ0_DRll_"+skimFilePrefix]->Fill(dRbetweenVectors(mu[0].p4,mu[1].p4),weight);
	      } else if(njs==1){
		histos["NJ1_ZPt_"+skimFilePrefix]->Fill(Z.Pt(),weight);
		histos["NJ1_ZEta_"+skimFilePrefix]->Fill(Z.Eta(),weight);
		histos["NJ1_ZPhi_"+skimFilePrefix]->Fill(Z.Phi(),weight);
		histos["NJ1_DPhill_"+skimFilePrefix]->Fill(getdphi(mu[0].p4.Phi(),mu[1].p4.Phi()),weight);
		histos["NJ1_DEtall_"+skimFilePrefix]->Fill(fabs(mu[0].p4.Eta()-mu[1].p4.Eta()),weight);
		histos["NJ1_DRll_"+skimFilePrefix]->Fill(dRbetweenVectors(mu[0].p4,mu[1].p4),weight);
	      } else if(njs==2){
		histos["NJ2_ZPt_"+skimFilePrefix]->Fill(Z.Pt(),weight);
		histos["NJ2_ZEta_"+skimFilePrefix]->Fill(Z.Eta(),weight);
		histos["NJ2_ZPhi_"+skimFilePrefix]->Fill(Z.Phi(),weight);
		histos["NJ2_DPhill_"+skimFilePrefix]->Fill(getdphi(mu[0].p4.Phi(),mu[1].p4.Phi()),weight);
		histos["NJ2_DEtall_"+skimFilePrefix]->Fill(fabs(mu[0].p4.Eta()-mu[1].p4.Eta()),weight);
		histos["NJ2_DRll_"+skimFilePrefix]->Fill(dRbetweenVectors(mu[0].p4,mu[1].p4),weight);
	      } else {
		histos["NJge3_ZPt_"+skimFilePrefix]->Fill(Z.Pt(),weight);
		histos["NJge3_ZEta_"+skimFilePrefix]->Fill(Z.Eta(),weight);
		histos["NJge3_ZPhi_"+skimFilePrefix]->Fill(Z.Phi(),weight);
		histos["NJge3_DPhill_"+skimFilePrefix]->Fill(getdphi(mu[0].p4.Phi(),mu[1].p4.Phi()),weight);
		histos["NJge3_DEtall_"+skimFilePrefix]->Fill(fabs(mu[0].p4.Eta()-mu[1].p4.Eta()),weight);
		histos["NJge3_DRll_"+skimFilePrefix]->Fill(dRbetweenVectors(mu[0].p4,mu[1].p4),weight);
	      } if(nbs==0){
		histos["NB0_ZPt_"+skimFilePrefix]->Fill(Z.Pt(),weight);
		histos["NB0_ZEta_"+skimFilePrefix]->Fill(Z.Eta(),weight);
		histos["NB0_ZPhi_"+skimFilePrefix]->Fill(Z.Phi(),weight);
		histos["NB0_DPhill_"+skimFilePrefix]->Fill(getdphi(mu[0].p4.Phi(),mu[1].p4.Phi()),weight);
		histos["NB0_DEtall_"+skimFilePrefix]->Fill(fabs(mu[0].p4.Eta()-mu[1].p4.Eta()),weight);
		histos["NB0_DRll_"+skimFilePrefix]->Fill(dRbetweenVectors(mu[0].p4,mu[1].p4),weight);
	      } else {
		histos["NBge1_ZPt_"+skimFilePrefix]->Fill(Z.Pt(),weight);
		histos["NBge1_ZEta_"+skimFilePrefix]->Fill(Z.Eta(),weight);
		histos["NBge1_ZPhi_"+skimFilePrefix]->Fill(Z.Phi(),weight);
		histos["NBge1_DPhill_"+skimFilePrefix]->Fill(getdphi(mu[0].p4.Phi(),mu[1].p4.Phi()),weight);
		histos["NBge1_DEtall_"+skimFilePrefix]->Fill(fabs(mu[0].p4.Eta()-mu[1].p4.Eta()),weight);
		histos["NBge1_DRll_"+skimFilePrefix]->Fill(dRbetweenVectors(mu[0].p4,mu[1].p4),weight);
	      } if(HT>100.){
		histos["HTge100_ZPt_"+skimFilePrefix]->Fill(Z.Pt(),weight);
		histos["HTge100_ZEta_"+skimFilePrefix]->Fill(Z.Eta(),weight);
		histos["HTge100_ZPhi_"+skimFilePrefix]->Fill(Z.Phi(),weight);
		histos["HTge100_DPhill_"+skimFilePrefix]->Fill(getdphi(mu[0].p4.Phi(),mu[1].p4.Phi()),weight);
		histos["HTge100_DEtall_"+skimFilePrefix]->Fill(fabs(mu[0].p4.Eta()-mu[1].p4.Eta()),weight);
		histos["HTge100_DRll_"+skimFilePrefix]->Fill(dRbetweenVectors(mu[0].p4,mu[1].p4),weight);
	      } if(HT>150.){
		histos["HTge150_ZPt_"+skimFilePrefix]->Fill(Z.Pt(),weight);
		histos["HTge150_ZEta_"+skimFilePrefix]->Fill(Z.Eta(),weight);
		histos["HTge150_ZPhi_"+skimFilePrefix]->Fill(Z.Phi(),weight);
		histos["HTge150_DPhill_"+skimFilePrefix]->Fill(getdphi(mu[0].p4.Phi(),mu[1].p4.Phi()),weight);
		histos["HTge150_DEtall_"+skimFilePrefix]->Fill(fabs(mu[0].p4.Eta()-mu[1].p4.Eta()),weight);
		histos["HTge150_DRll_"+skimFilePrefix]->Fill(dRbetweenVectors(mu[0].p4,mu[1].p4),weight);
	      } if(p.evt_pfmet>50.){
		histos["METge50_ZPt_"+skimFilePrefix]->Fill(Z.Pt(),weight);
		histos["METge50_ZEta_"+skimFilePrefix]->Fill(Z.Eta(),weight);
		histos["METge50_ZPhi_"+skimFilePrefix]->Fill(Z.Phi(),weight);
		histos["METge50_DPhill_"+skimFilePrefix]->Fill(getdphi(mu[0].p4.Phi(),mu[1].p4.Phi()),weight);
		histos["METge50_DEtall_"+skimFilePrefix]->Fill(fabs(mu[0].p4.Eta()-mu[1].p4.Eta()),weight);
		histos["METge50_DRll_"+skimFilePrefix]->Fill(dRbetweenVectors(mu[0].p4,mu[1].p4),weight);
	      } if(p.evt_pfmet>25.){
		histos["METge25_ZPt_"+skimFilePrefix]->Fill(Z.Pt(),weight);
		histos["METge25_ZEta_"+skimFilePrefix]->Fill(Z.Eta(),weight);
		histos["METge25_ZPhi_"+skimFilePrefix]->Fill(Z.Phi(),weight);
		histos["METge25_DPhill_"+skimFilePrefix]->Fill(getdphi(mu[0].p4.Phi(),mu[1].p4.Phi()),weight);
		histos["METge25_DEtall_"+skimFilePrefix]->Fill(fabs(mu[0].p4.Eta()-mu[1].p4.Eta()),weight);
		histos["METge25_DRll_"+skimFilePrefix]->Fill(dRbetweenVectors(mu[0].p4,mu[1].p4),weight);	
	      }
	      for(unsigned int i = 0; i<mu.size(); ++i){
		float mucharge = 0; if(mu[i].id==13) mucharge = -1; else if(mu[i].id==-13) mucharge = +1; 
		histos["MuPt_"+skimFilePrefix]->Fill(mu[i].p4.Pt(),weight);
		histos["MuEta_"+skimFilePrefix]->Fill(mu[i].p4.Eta(),weight);
		histos["MuPhi_"+skimFilePrefix]->Fill(mu[i].p4.Phi(),weight);
		histos["MuCharge_"+skimFilePrefix]->Fill(mucharge,weight);
		if(njs==0){
		  histos["NJ0_MuPt_"+skimFilePrefix]->Fill(mu[i].p4.Pt(),weight);
		  histos["NJ0_MuEta_"+skimFilePrefix]->Fill(mu[i].p4.Eta(),weight);
		  histos["NJ0_MuPhi_"+skimFilePrefix]->Fill(mu[i].p4.Phi(),weight);
		  histos["NJ0_MuCharge_"+skimFilePrefix]->Fill(mucharge,weight);
		} else if(njs==1){
		  histos["NJ1_MuPt_"+skimFilePrefix]->Fill(mu[i].p4.Pt(),weight);
		  histos["NJ1_MuEta_"+skimFilePrefix]->Fill(mu[i].p4.Eta(),weight);
		  histos["NJ1_MuPhi_"+skimFilePrefix]->Fill(mu[i].p4.Phi(),weight);
		  histos["NJ1_MuCharge_"+skimFilePrefix]->Fill(mucharge,weight);
		} else if(njs==2){
		  histos["NJ2_MuPt_"+skimFilePrefix]->Fill(mu[i].p4.Pt(),weight);
		  histos["NJ2_MuEta_"+skimFilePrefix]->Fill(mu[i].p4.Eta(),weight);
		  histos["NJ2_MuPhi_"+skimFilePrefix]->Fill(mu[i].p4.Phi(),weight);
		  histos["NJ2_MuCharge_"+skimFilePrefix]->Fill(mucharge,weight);
		} else {
		  histos["NJge3_MuPt_"+skimFilePrefix]->Fill(mu[i].p4.Pt(),weight);
		  histos["NJge3_MuEta_"+skimFilePrefix]->Fill(mu[i].p4.Eta(),weight);
		  histos["NJge3_MuPhi_"+skimFilePrefix]->Fill(mu[i].p4.Phi(),weight);
		  histos["NJge3_MuCharge_"+skimFilePrefix]->Fill(mucharge,weight);
		} if(nbs==0){
		  histos["NB0_MuPt_"+skimFilePrefix]->Fill(mu[i].p4.Pt(),weight);
		  histos["NB0_MuEta_"+skimFilePrefix]->Fill(mu[i].p4.Eta(),weight);
		  histos["NB0_MuPhi_"+skimFilePrefix]->Fill(mu[i].p4.Phi(),weight);
		  histos["NB0_MuCharge_"+skimFilePrefix]->Fill(mucharge,weight);
		} else {
		  histos["NBge1_MuPt_"+skimFilePrefix]->Fill(mu[i].p4.Pt(),weight);
		  histos["NBge1_MuEta_"+skimFilePrefix]->Fill(mu[i].p4.Eta(),weight);
		  histos["NBge1_MuPhi_"+skimFilePrefix]->Fill(mu[i].p4.Phi(),weight);
		  histos["NBge1_MuCharge_"+skimFilePrefix]->Fill(mucharge,weight);
		} if(HT>100.){
		  histos["HTge100_MuPt_"+skimFilePrefix]->Fill(mu[i].p4.Pt(),weight);
		  histos["HTge100_MuEta_"+skimFilePrefix]->Fill(mu[i].p4.Eta(),weight);
		  histos["HTge100_MuPhi_"+skimFilePrefix]->Fill(mu[i].p4.Phi(),weight);
		  histos["HTge100_MuCharge_"+skimFilePrefix]->Fill(mucharge,weight);
		} if(HT>150.){
		  histos["HTge150_MuPt_"+skimFilePrefix]->Fill(mu[i].p4.Pt(),weight);
		  histos["HTge150_MuEta_"+skimFilePrefix]->Fill(mu[i].p4.Eta(),weight);
		  histos["HTge150_MuPhi_"+skimFilePrefix]->Fill(mu[i].p4.Phi(),weight);
		  histos["HTge150_MuCharge_"+skimFilePrefix]->Fill(mucharge,weight);
		} if(p.evt_pfmet>50.){
		  histos["METge50_MuPt_"+skimFilePrefix]->Fill(mu[i].p4.Pt(),weight);
		  histos["METge50_MuEta_"+skimFilePrefix]->Fill(mu[i].p4.Eta(),weight);
		  histos["METge50_MuPhi_"+skimFilePrefix]->Fill(mu[i].p4.Phi(),weight);
		  histos["METge50_MuCharge_"+skimFilePrefix]->Fill(mucharge,weight);
		} if(p.evt_pfmet>25.){
		  histos["METge25_MuPt_"+skimFilePrefix]->Fill(mu[i].p4.Pt(),weight);
		  histos["METge25_MuEta_"+skimFilePrefix]->Fill(mu[i].p4.Eta(),weight);
		  histos["METge25_MuPhi_"+skimFilePrefix]->Fill(mu[i].p4.Phi(),weight);
		  histos["METge25_MuCharge_"+skimFilePrefix]->Fill(mucharge,weight);
		}
	      }
	    }
	  }
	  if((triggerbool1mu||triggerbool2mu)&& mu[0].passes_POG_tightID&&mu[1].passes_POG_tightID&&fabs(mu[0].dZ)<0.1&&fabs(mu[1].dZ)<0.1&&fabs(mu[0].dxyPV)<0.02&&fabs(mu[1].dxyPV)<0.02){
	    if(Z.M()>75.&&Z.M()<105){
	      for(unsigned int i = 0; i<mu.size(); ++i){
		histos["MuRelIso03_"+skimFilePrefix]->Fill(mu[i].RelIso03,weight);
		histos["MuRelIso03EA_"+skimFilePrefix]->Fill(mu[i].RelIso03EA,weight);
		histos["MuRelIso03DB_"+skimFilePrefix]->Fill(mu[i].RelIso03DB,weight);
		histos["MuMiniIsoEA_"+skimFilePrefix]->Fill(mu[i].miniiso,weight);
		histos["MuMiniIsoDB_"+skimFilePrefix]->Fill(mu[i].miniisoDB,weight);
		histos["MuRelIso04_"+skimFilePrefix]->Fill(mu[i].reliso04,weight);
		histos["MuAnnulus04_"+skimFilePrefix]->Fill(mu[i].annulus04,weight);
		if(mu[0].mt>30&&mu[0].mt>30){
		  histos["MuRelIso03_MT30_"+skimFilePrefix]->Fill(mu[i].RelIso03,weight);
		  histos["MuRelIso03EA_MT30_"+skimFilePrefix]->Fill(mu[i].RelIso03EA,weight);
		  histos["MuRelIso03DB_MT30_"+skimFilePrefix]->Fill(mu[i].RelIso03DB,weight);
		  histos["MuMiniIsoEA_MT30_"+skimFilePrefix]->Fill(mu[i].miniiso,weight);
		  histos["MuMiniIsoDB_MT30_"+skimFilePrefix]->Fill(mu[i].miniisoDB,weight);
		  histos["MuRelIso04_MT30_"+skimFilePrefix]->Fill(mu[i].reliso04,weight);
		  histos["MuAnnulus04_MT30_"+skimFilePrefix]->Fill(mu[i].annulus04,weight);
		}
	      }
	    }
	  }
	  if((triggerbool1mu||triggerbool2mu)&& mu[0].passes_POG_tightID&&mu[1].passes_POG_tightID&&mu[0].miniisoDB<0.2&&mu[1].miniisoDB<0.2){
	    if(Z.M()>75.&&Z.M()<105){
	      for(unsigned int i = 0; i<mu.size(); ++i){
		histos["Mud0_"+skimFilePrefix]->Fill(mu[i].dxyPV,weight);
		histos["MudZ_"+skimFilePrefix]->Fill(mu[i].dZ,weight);
		histos["MuIP3d_"+skimFilePrefix]->Fill(mu[i].ip3d,weight);
	      }
	    }
	  }
	  if((triggerbool1mu||triggerbool2mu)&& mu[0].passes_POG_looseID&&mu[1].passes_POG_looseID&&mu[0].miniisoDB<0.2&&mu[1].miniisoDB<0.2&&
	      fabs(mu[0].dZ)<0.1&&fabs(mu[1].dZ)<0.1&&fabs(mu[0].dxyPV)<0.02&&fabs(mu[1].dxyPV)<0.02){
	    if(Z.M()>75.&&Z.M()<105){
	      for(unsigned int i = 0; i<mu.size(); ++i){
		if(mu[i].passes_POG_tightID) histos["MuID_"+skimFilePrefix]->Fill(3.,weight);
		else if(mu[i].passes_POG_mediumID) histos["MuID_"+skimFilePrefix]->Fill(2.,weight);
		else if(mu[i].passes_POG_looseID) histos["MuID_"+skimFilePrefix]->Fill(1.,weight);
		histos["MuvalidFraction_"+skimFilePrefix]->Fill((float)mu[i].validHits/((float)(mu[i].validHits+mu[i].lostHits+mu[i].exp_innerlayers+mu[i].exp_outerlayers)),weight);
		if(mu[i].gfit_ndof>0) histos["Mugfit_normchi2_"+skimFilePrefix]->Fill(mu[i].gfit_chi2/mu[i].gfit_ndof, weight);
		histos["Mugfit_validSTAHits_"+skimFilePrefix]->Fill(mu[i].gfit_validSTAHits,weight);
		histos["MunumberOfMatchedStations_"+skimFilePrefix]->Fill(mu[i].numberOfMatchedStations,weight);
		histos["MuvalidPixelHits_"+skimFilePrefix]->Fill(mu[i].validPixelHits,weight);
		histos["Munlayers_"+skimFilePrefix]->Fill(mu[i].nlayers,weight);
		histos["Muchi2LocalPosition_"+skimFilePrefix]->Fill(mu[i].chi2LocalPosition,weight);
		histos["MutrkKink_"+skimFilePrefix]->Fill(mu[i].trkKink,weight);
		histos["MusegmCompatibility_"+skimFilePrefix]->Fill(mu[i].segmCompatibility,weight);
	      }
	    }
	  }
	}//2 muons
	else if(mu.size()==1){
	  triggerbool1mu = triggerbool1mu&&((mu[0].p4.Pt()>30.&&fabs(mu[0].p4.Eta())<2.1));//one muon passing nominal trigger w/o iso
	  if(triggerbool1mu&&mu[0].passes_POG_tightID&&mu[0].miniisoDB<0.2&&fabs(mu[0].dZ)<0.1&&fabs(mu[0].dxyPV)<0.02&&mu[0].mt>40){//1 mu events.
	    float mucharge = 0; if(mu[0].id==13) mucharge = -1; else if(mu[0].id==-13) mucharge = +1; 
	    histos["MT_"+skimFilePrefix]->Fill(mu[0].mt,weight);
	    histos["MyMuPt_"+skimFilePrefix]->Fill(mu[0].p4.Pt(),weight);
	    histos["MyMuEta_"+skimFilePrefix]->Fill(mu[0].p4.Eta(),weight);
	    histos["MyMuPhi_"+skimFilePrefix]->Fill(mu[0].p4.Phi(),weight);
	    histos["MyMuCharge_"+skimFilePrefix]->Fill(mucharge,weight);
	    if(njs==0){
	      histos["NJ0_MT_"+skimFilePrefix]->Fill(mu[0].mt,weight);
	      histos["NJ0_MyMuPt_"+skimFilePrefix]->Fill(mu[0].p4.Pt(),weight);
	      histos["NJ0_MyMuEta_"+skimFilePrefix]->Fill(mu[0].p4.Eta(),weight);
	      histos["NJ0_MyMuPhi_"+skimFilePrefix]->Fill(mu[0].p4.Phi(),weight);
	      histos["NJ0_MyMuCharge_"+skimFilePrefix]->Fill(mucharge,weight);
	    } else if(njs==1){
	      histos["NJ1_MT_"+skimFilePrefix]->Fill(mu[0].mt,weight);
	      histos["NJ1_MyMuPt_"+skimFilePrefix]->Fill(mu[0].p4.Pt(),weight);
	      histos["NJ1_MyMuEta_"+skimFilePrefix]->Fill(mu[0].p4.Eta(),weight);
	      histos["NJ1_MyMuPhi_"+skimFilePrefix]->Fill(mu[0].p4.Phi(),weight);
	      histos["NJ1_MyMuCharge_"+skimFilePrefix]->Fill(mucharge,weight);	      
	    } else if(njs==2){
	      histos["NJ2_MT_"+skimFilePrefix]->Fill(mu[0].mt,weight);
	      histos["NJ2_MyMuPt_"+skimFilePrefix]->Fill(mu[0].p4.Pt(),weight);
	      histos["NJ2_MyMuEta_"+skimFilePrefix]->Fill(mu[0].p4.Eta(),weight);
	      histos["NJ2_MyMuPhi_"+skimFilePrefix]->Fill(mu[0].p4.Phi(),weight);
	      histos["NJ2_MyMuCharge_"+skimFilePrefix]->Fill(mucharge,weight);	      
	    } else {
	      histos["NJge3_MT_"+skimFilePrefix]->Fill(mu[0].mt,weight);
	      histos["NJge3_MyMuPt_"+skimFilePrefix]->Fill(mu[0].p4.Pt(),weight);
	      histos["NJge3_MyMuEta_"+skimFilePrefix]->Fill(mu[0].p4.Eta(),weight);
	      histos["NJge3_MyMuPhi_"+skimFilePrefix]->Fill(mu[0].p4.Phi(),weight);
	      histos["NJge3_MyMuCharge_"+skimFilePrefix]->Fill(mucharge,weight);	      
	    } if(nbs==0){
	      histos["NB0_MT_"+skimFilePrefix]->Fill(mu[0].mt,weight);
	      histos["NB0_MyMuPt_"+skimFilePrefix]->Fill(mu[0].p4.Pt(),weight);
	      histos["NB0_MyMuEta_"+skimFilePrefix]->Fill(mu[0].p4.Eta(),weight);
	      histos["NB0_MyMuPhi_"+skimFilePrefix]->Fill(mu[0].p4.Phi(),weight);
	      histos["NB0_MyMuCharge_"+skimFilePrefix]->Fill(mucharge,weight);	      
	    } else {
	      histos["NBge1_MT_"+skimFilePrefix]->Fill(mu[0].mt,weight);
	      histos["NBge1_MyMuPt_"+skimFilePrefix]->Fill(mu[0].p4.Pt(),weight);
	      histos["NBge1_MyMuEta_"+skimFilePrefix]->Fill(mu[0].p4.Eta(),weight);
	      histos["NBge1_MyMuPhi_"+skimFilePrefix]->Fill(mu[0].p4.Phi(),weight);
	      histos["NBge1_MyMuCharge_"+skimFilePrefix]->Fill(mucharge,weight);	      
	    } if(HT>100.){
	      histos["HTge100_MT_"+skimFilePrefix]->Fill(mu[0].mt,weight);
	      histos["HTge100_MyMuPt_"+skimFilePrefix]->Fill(mu[0].p4.Pt(),weight);
	      histos["HTge100_MyMuEta_"+skimFilePrefix]->Fill(mu[0].p4.Eta(),weight);
	      histos["HTge100_MyMuPhi_"+skimFilePrefix]->Fill(mu[0].p4.Phi(),weight);
	      histos["HTge100_MyMuCharge_"+skimFilePrefix]->Fill(mucharge,weight);	      
	    } if(HT>150.){
	      histos["HTge150_MT_"+skimFilePrefix]->Fill(mu[0].mt,weight);
	      histos["HTge150_MyMuPt_"+skimFilePrefix]->Fill(mu[0].p4.Pt(),weight);
	      histos["HTge150_MyMuEta_"+skimFilePrefix]->Fill(mu[0].p4.Eta(),weight);
	      histos["HTge150_MyMuPhi_"+skimFilePrefix]->Fill(mu[0].p4.Phi(),weight);
	      histos["HTge150_MyMuCharge_"+skimFilePrefix]->Fill(mucharge,weight);	      
	    } if(p.evt_pfmet>50.){
	      histos["METge50_MT_"+skimFilePrefix]->Fill(mu[0].mt,weight);
	      histos["METge50_MyMuPt_"+skimFilePrefix]->Fill(mu[0].p4.Pt(),weight);
	      histos["METge50_MyMuEta_"+skimFilePrefix]->Fill(mu[0].p4.Eta(),weight);
	      histos["METge50_MyMuPhi_"+skimFilePrefix]->Fill(mu[0].p4.Phi(),weight);
	      histos["METge50_MyMuCharge_"+skimFilePrefix]->Fill(mucharge,weight);	      
	    } if(p.evt_pfmet>25.){
	      histos["METge25_MT_"+skimFilePrefix]->Fill(mu[0].mt,weight);
	      histos["METge25_MyMuPt_"+skimFilePrefix]->Fill(mu[0].p4.Pt(),weight);
	      histos["METge25_MyMuEta_"+skimFilePrefix]->Fill(mu[0].p4.Eta(),weight);
	      histos["METge25_MyMuPhi_"+skimFilePrefix]->Fill(mu[0].p4.Phi(),weight);
	      histos["METge25_MyMuCharge_"+skimFilePrefix]->Fill(mucharge,weight);	      
	    }
	  }
	}
      }
      if(!sameEvent(p,c)){
	//finally start new event.
	if(abs(p.id)==13&&p.passes_POG_tightID&&p.miniisoDB<0.2&&fabs(p.dZ)<0.1&&fabs(p.dxyPV)<0.02&&p.dilep_mass>75.&&p.dilep_mass<105&&p.p4.Pt()>20&&fabs(p.p4.Eta())<2.1) {
	  if((p.evt_isRealData&&(p.HLT_Mu17_TrkIsoVVL_Mu8_TrkIsoVVL_DZ || p.HLT_Mu17_TrkIsoVVL_TkMu8_TrkIsoVVL_DZ || p.HLT_IsoMu24_eta2p1 || p.HLT_IsoTkMu24_eta2p1 || p.HLT_IsoMu27 || p.HLT_IsoTkMu27 || p.HLT_IsoMu20 || p.HLT_IsoMu20))||(!p.evt_isRealData)){
	    histos["Z_Pt_"+skimFilePrefix]->Fill(p.dilep_p4.Pt(),weight);
	  }
	}
	mu.clear();
	nleps = 1;
      }
      if(currentrun!=c.evt_run) { cout << "This is run " << c.evt_run << endl; currentrun = c.evt_run; }
      bool skip = false;
      //if(c.evt_run!=251244&&c.evt_run!=251251&&c.evt_run!=251252) skip = true;
      if(abs(c.id)!=13) skip = true;
      else if(c.p4.Pt()<20.) skip = true;
      else if(fabs(c.p4.Eta())>2.1) skip = true;
      else if(!c.passes_POG_looseID) skip = true;
      //else if(fabs(c.dZ)>0.5) skip = true;
      //else if(fabs(c.dxyPV)>0.2) skip = true;
      //else if(c.miniisoDB>0.5) skip = true;
      if(!skip) { mu.push_back(c); }
      p = c;
      resetEvent(c);
    }
  
    // Clean Up
    delete tree;
    file->Close();
    delete file;
  }
  if ( nEventsChain != nEventsTotal ) {
    cout << Form( "ERROR: number of events from files (%d) is not equal to total number of events (%d)", nEventsChain, nEventsTotal ) << endl;
  }
  
  // Example Histograms
  for(map<string,TH1F*>::iterator h=histos.begin(); h!=histos.end();++h){
    h->second->SetBinContent(h->second->GetNbinsX(), h->second->GetBinContent(h->second->GetNbinsX() )+ h->second->GetBinContent(h->second->GetNbinsX()+1) );
    h->second->SetBinError(h->second->GetNbinsX(), sqrt(pow(h->second->GetBinError(h->second->GetNbinsX() ),2)+pow(h->second->GetBinError(h->second->GetNbinsX()+1),2) ) );
  }
  for(map<string,TH1F*>::iterator h=histos.begin(); h!=histos.end();++h){
    h->second->SetBinContent(1, h->second->GetBinContent(1 )+ h->second->GetBinContent(0) );
    h->second->SetBinError(1, sqrt(pow(h->second->GetBinError(1 ),2)+pow(h->second->GetBinError(0),2) ) );
  }
  //string filename = "rootfiles/test/Histos_"+skimFilePrefix+".root";
  string filename = "rootfiles/first_20150727/Histos3_"+skimFilePrefix+".root";
  if(DCSonly) filename = "rootfiles/first_20150727/Histos3DCS_"+skimFilePrefix+".root";
  TFile *f = new TFile(filename.c_str(),"RECREATE");
  f->cd();
  for(map<string,TH1F*>::iterator h=    histos.begin(); h!=    histos.end();++h) h->second->Write();
  f->Close();
  cout << "Saved histos in " << f->GetName() << endl;  
  // return
  bmark->Stop("benchmark");
  cout << endl;
  cout << nEventsTotal << " Events Processed" << endl;
  cout << "------------------------------" << endl;
  cout << "CPU  Time:	" << Form( "%.01f", bmark->GetCpuTime("benchmark")  ) << endl;
  cout << "Real Time:	" << Form( "%.01f", bmark->GetRealTime("benchmark") ) << endl;
  cout << endl;
  delete bmark;
  return 0;
}
Пример #8
0
void selectZee(const TString conf,        // input file
               const TString outputDir,   // output directory
	       const Bool_t  doScaleCorr  // apply energy scale corrections?
) {
  gBenchmark->Start("selectZee");

  //--------------------------------------------------------------------------------------------------------------
  // Settings 
  //============================================================================================================== 

  const Double_t MASS_LOW  = 40;
  const Double_t MASS_HIGH = 200;
  const Double_t PT_CUT    = 20;
  const Double_t ETA_CUT   = 2.5;
  const Double_t ELE_MASS  = 0.000511;
  
  const Double_t ECAL_GAP_LOW  = 1.4442;
  const Double_t ECAL_GAP_HIGH = 1.566;
  
  const Double_t escaleNbins  = 6;
  const Double_t escaleEta[]  = { 0.4,     0.8,     1.2,     1.4442,  2,        2.5 };
  const Double_t escaleCorr[] = { 1.00284, 1.00479, 1.00734, 1.00851, 1.00001,  0.982898 };


  //--------------------------------------------------------------------------------------------------------------
  // Main analysis code 
  //==============================================================================================================  

  enum { eEleEle2HLT=1, eEleEle1HLT, eEleEleNoSel, eEleSC };  // event category enum
  
  vector<TString>  snamev;      // sample name (for output files)  
  vector<CSample*> samplev;     // data/MC samples

  //
  // parse .conf file
  //
  confParse(conf, snamev, samplev);
  const Bool_t hasData = (samplev[0]->fnamev.size()>0);

  // Create output directory
  gSystem->mkdir(outputDir,kTRUE);
  const TString ntupDir = outputDir + TString("/ntuples");
  gSystem->mkdir(ntupDir,kTRUE);
  
  //
  // Declare output ntuple variables
  //
  UInt_t  runNum, lumiSec, evtNum;
  UInt_t  matchGen;
  UInt_t  category;
  UInt_t  npv, npu;
  Float_t genVPt, genVPhi, genVy, genVMass;
  Float_t scale1fb;
  Float_t met, metPhi, sumEt, u1, u2;
  Int_t   q1, q2;
  LorentzVector *dilep=0, *lep1=0, *lep2=0;
  ///// electron specific /////
  Float_t trkIso1, emIso1, hadIso1, trkIso2, emIso2, hadIso2;
  Float_t pfChIso1, pfGamIso1, pfNeuIso1, pfCombIso1, pfChIso2, pfGamIso2, pfNeuIso2, pfCombIso2;
  Float_t sigieie1, hovere1, eoverp1, fbrem1, ecalE1, sigieie2, hovere2, eoverp2, fbrem2, ecalE2;
  Float_t dphi1, deta1, dphi2, deta2;
  Float_t d01, dz1, d02, dz2;
  UInt_t  isConv1, nexphits1, typeBits1, isConv2, nexphits2, typeBits2; 
  LorentzVector *sc1=0, *sc2=0;
  
  // Data structures to store info from TTrees
  mithep::TEventInfo *info  = new mithep::TEventInfo();
  mithep::TGenInfo   *gen   = new mithep::TGenInfo();
  TClonesArray *electronArr = new TClonesArray("mithep::TElectron");
  TClonesArray *scArr       = new TClonesArray("mithep::TPhoton");
  TClonesArray *pvArr       = new TClonesArray("mithep::TVertex");
  
  TFile *infile=0;
  TTree *eventTree=0;
  
  //
  // loop over samples
  //  
  for(UInt_t isam=0; isam<samplev.size(); isam++) {
    
    // Assume data sample is first sample in .conf file
    // If sample is empty (i.e. contains no ntuple files), skip to next sample
    if(isam==0 && !hasData) continue;
    
    // Assume signal sample is given name "zee"
    // If it's the signal sample, toggle flag to store GEN W kinematics
    Bool_t isSignal = (snamev[isam].CompareTo("zee",TString::kIgnoreCase)==0);  
    
    CSample* samp = samplev[isam];
  
    //
    // Set up output ntuple
    //
    TString outfilename = ntupDir + TString("/") + snamev[isam] + TString("_select.root");
    if(isam==0 && !doScaleCorr) outfilename = ntupDir + TString("/") + snamev[isam] + TString("_select.raw.root");
    TFile *outFile = new TFile(outfilename,"RECREATE"); 
    TTree *outTree = new TTree("Events","Events");

    outTree->Branch("runNum",   &runNum,   "runNum/i");     // event run number
    outTree->Branch("lumiSec",  &lumiSec,  "lumiSec/i");    // event lumi section
    outTree->Branch("evtNum",   &evtNum,   "evtNum/i");     // event number
    outTree->Branch("matchGen", &matchGen, "matchGen/i");   // event has both leptons matched to MC Z->ll
    outTree->Branch("category", &category, "category/i");   // dilepton category
    outTree->Branch("npv",      &npv,      "npv/i");        // number of primary vertices
    outTree->Branch("npu",      &npu,      "npu/i");        // number of in-time PU events (MC)
    outTree->Branch("genVPt",   &genVPt,   "genVPt/F");     // GEN boson pT (signal MC)
    outTree->Branch("genVPhi",  &genVPhi,  "genVPhi/F");    // GEN boson phi (signal MC)
    outTree->Branch("genVy",    &genVy,    "genVy/F");      // GEN boson rapidity (signal MC)
    outTree->Branch("genVMass", &genVMass, "genVMass/F");   // GEN boson mass (signal MC)
    outTree->Branch("scale1fb", &scale1fb, "scale1fb/F");   // event weight per 1/fb (MC)
    outTree->Branch("met",      &met,      "met/F");        // MET
    outTree->Branch("metPhi",   &metPhi,   "metPhi/F");     // phi(MET)
    outTree->Branch("sumEt",    &sumEt,    "sumEt/F");      // Sum ET
    outTree->Branch("u1",       &u1,       "u1/F");         // parallel component of recoil
    outTree->Branch("u2",       &u2,       "u2/F");         // perpendicular component of recoil
    outTree->Branch("q1",       &q1,       "q1/I");         // charge of tag lepton
    outTree->Branch("q2",       &q2,       "q2/I");         // charge of probe lepton
    outTree->Branch("dilep", "ROOT::Math::LorentzVector<ROOT::Math::PtEtaPhiM4D<double> >", &dilep);  // dilepton 4-vector
    outTree->Branch("lep1",  "ROOT::Math::LorentzVector<ROOT::Math::PtEtaPhiM4D<double> >", &lep1);   // tag lepton 4-vector
    outTree->Branch("lep2",  "ROOT::Math::LorentzVector<ROOT::Math::PtEtaPhiM4D<double> >", &lep2);   // probe lepton 4-vector
    ///// electron specific /////
    outTree->Branch("trkIso1",    &trkIso1,    "trkIso1/F");     // track isolation of tag lepton
    outTree->Branch("trkIso2",    &trkIso2,    "trkIso2/F");     // track isolation of probe lepton
    outTree->Branch("emIso1",     &emIso1,     "emIso1/F");      // ECAL isolation of tag lepton
    outTree->Branch("emIso2",     &emIso2,     "emIso2/F");      // ECAL isolation of probe lepton
    outTree->Branch("hadIso1",    &hadIso1,    "hadIso1/F");     // HCAL isolation of tag lepton
    outTree->Branch("hadIso2",    &hadIso2,    "hadIso2/F");     // HCAL isolation of probe lepton
    outTree->Branch("pfChIso1",   &pfChIso1,   "pfChIso1/F");    // PF charged hadron isolation of tag lepton
    outTree->Branch("pfChIso2",   &pfChIso2,   "pfChIso2/F");    // PF charged hadron isolation of probe lepton
    outTree->Branch("pfGamIso1",  &pfGamIso1,  "pfGamIso1/F");   // PF photon isolation of tag lepton
    outTree->Branch("pfGamIso2",  &pfGamIso2,  "pfGamIso2/F");   // PF photon isolation of probe lepton
    outTree->Branch("pfNeuIso1",  &pfNeuIso1,  "pfNeuIso1/F");   // PF neutral hadron isolation of tag lepton
    outTree->Branch("pfNeuIso2",  &pfNeuIso2,  "pfNeuIso2/F");   // PF neutral hadron isolation of probe lepton
    outTree->Branch("pfCombIso1", &pfCombIso1, "pfCombIso1/F");  // PF combine isolation of tag lepton
    outTree->Branch("pfCombIso2", &pfCombIso2, "pfCombIso2/F");  // PF combined isolation of probe lepton    
    outTree->Branch("sigieie1",   &sigieie1,   "sigieie1/F");    // sigma-ieta-ieta of tag
    outTree->Branch("sigieie2",   &sigieie2,   "sigieie2/F");    // sigma-ieta-ieta of probe
    outTree->Branch("hovere1",    &hovere1,    "hovere1/F");     // H/E of tag
    outTree->Branch("hovere2",    &hovere2,    "hovere2/F");     // H/E of probe
    outTree->Branch("eoverp1",    &eoverp1,    "eoverp1/F");     // E/p of tag
    outTree->Branch("eoverp2",    &eoverp2,    "eoverp2/F");     // E/p of probe	 
    outTree->Branch("fbrem1",     &fbrem1,     "fbrem1/F");      // brem fraction of tag
    outTree->Branch("fbrem2",     &fbrem2,     "fbrem2/F");      // brem fraction of probe
    outTree->Branch("dphi1",      &dphi1,      "dphi1/F");       // GSF track - ECAL dphi of tag
    outTree->Branch("dphi2",      &dphi2,      "dphi2/F");       // GSF track - ECAL dphi of probe 	
    outTree->Branch("deta1",      &deta1,      "deta1/F");       // GSF track - ECAL deta of tag
    outTree->Branch("deta2",      &deta2,      "deta2/F");       // GSF track - ECAL deta of probe
    outTree->Branch("ecalE1",     &ecalE1,     "ecalE1/F");      // ECAL energy of tag
    outTree->Branch("ecalE2",     &ecalE2,     "ecalE2/F");      // ECAL energy of probe
    outTree->Branch("d01",        &d01,        "d01/F");	 // transverse impact parameter of tag
    outTree->Branch("d02",        &d02,        "d02/F");	 // transverse impact parameter of probe	  
    outTree->Branch("dz1",        &dz1,        "dz1/F");	 // longitudinal impact parameter of tag
    outTree->Branch("dz2",        &dz2,        "dz2/F");	 // longitudinal impact parameter of probe
    outTree->Branch("isConv1",    &isConv1,    "isConv1/i");     // conversion filter flag of tag lepton
    outTree->Branch("isConv2",    &isConv2,    "isConv2/i");     // conversion filter flag of probe lepton
    outTree->Branch("nexphits1",  &nexphits1,  "nexphits1/i");   // number of missing expected inner hits of tag lepton
    outTree->Branch("nexphits2",  &nexphits2,  "nexphits2/i");   // number of missing expected inner hits of probe lepton
    outTree->Branch("typeBits1",  &typeBits1,  "typeBits1/i");   // electron type of tag lepton
    outTree->Branch("typeBits2",  &typeBits2,  "typeBits2/i");   // electron type of probe lepton
    outTree->Branch("sc1",  "ROOT::Math::LorentzVector<ROOT::Math::PtEtaPhiM4D<double> >", &sc1);   // tag Supercluster 4-vector
    outTree->Branch("sc2",  "ROOT::Math::LorentzVector<ROOT::Math::PtEtaPhiM4D<double> >", &sc2);   // probe Supercluster 4-vector 
    
    //
    // loop through files
    //
    const UInt_t nfiles = samp->fnamev.size();
    for(UInt_t ifile=0; ifile<nfiles; ifile++) {  

      // Read input file and get the TTrees
      cout << "Processing " << samp->fnamev[ifile] << " [xsec = " << samp->xsecv[ifile] << " pb] ... "; cout.flush();
      infile = new TFile(samp->fnamev[ifile]); 
      assert(infile);

      Bool_t hasJSON = kFALSE;
      mithep::RunLumiRangeMap rlrm;
      if(samp->jsonv[ifile].CompareTo("NONE")!=0) { 
        hasJSON = kTRUE;
        rlrm.AddJSONFile(samp->jsonv[ifile].Data()); 
      }
  
      eventTree = (TTree*)infile->Get("Events");
      assert(eventTree);  
      eventTree->SetBranchAddress("Info",     &info);        TBranch *infoBr     = eventTree->GetBranch("Info");
      eventTree->SetBranchAddress("Electron", &electronArr); TBranch *electronBr = eventTree->GetBranch("Electron");
      eventTree->SetBranchAddress("Photon",   &scArr);       TBranch *scBr       = eventTree->GetBranch("Photon");
      eventTree->SetBranchAddress("PV",       &pvArr);       TBranch *pvBr       = eventTree->GetBranch("PV");
      Bool_t hasGen = eventTree->GetBranchStatus("Gen");
      TBranch *genBr=0;
      if(hasGen) {
        eventTree->SetBranchAddress("Gen", &gen);
	genBr = eventTree->GetBranch("Gen");
      }
      
      // Compute MC event weight per 1/fb
      Double_t weight = 1;
      const Double_t xsec = samp->xsecv[ifile];
      if(xsec>0) weight = 1000.*xsec/(Double_t)eventTree->GetEntries();     

      //
      // loop over events
      //
      Double_t nsel=0, nselvar=0;
      for(UInt_t ientry=0; ientry<eventTree->GetEntries(); ientry++) {
        infoBr->GetEntry(ientry);
	
	if(genBr) genBr->GetEntry(ientry);
     
        // check for certified lumi (if applicable)
        mithep::RunLumiRangeMap::RunLumiPairType rl(info->runNum, info->lumiSec);      
        if(hasJSON && !rlrm.HasRunLumi(rl)) continue;  

        // trigger requirement               
        ULong64_t trigger = kHLT_Ele22_CaloIdL_CaloIsoVL;
	ULong64_t trigObj = kHLT_Ele22_CaloIdL_CaloIsoVL_EleObj;  
        if(!(info->triggerBits & trigger)) continue;      
      
        // good vertex requirement
        if(!(info->hasGoodPV)) continue;
        pvArr->Clear();
        pvBr->GetEntry(ientry);
      
        //
	// SELECTION PROCEDURE:
	//  (1) Find a good electron matched to trigger -> this will be the "tag"
	//  (2) Pair the tag with Supercluster probes which form a tag+probe mass inside 
	//      the Z window and divide candidates into exclusive categories as follows:
	//      (a) if probe SC is part of a good electron matched to trigger     -> EleEle2HLT category
	//      (b) if probe SC is part of a good electron not matched to trigger -> EleEle1HLT category
	//      (c) if probe SC is part of an electron failing selection cuts     -> EleEleNoSel category
	//      (d) if probe SC is not part of an ECAL driven electron            -> EleSC category
	//	
	electronArr->Clear();
        electronBr->GetEntry(ientry);
	scArr->Clear();
	scBr->GetEntry(ientry);
        for(Int_t i1=0; i1<electronArr->GetEntriesFast(); i1++) {
          const mithep::TElectron *tag = (mithep::TElectron*)((*electronArr)[i1]);
	  
	  // check ECAL gap
	  if(fabs(tag->scEta)>=ECAL_GAP_LOW && fabs(tag->scEta)<=ECAL_GAP_HIGH) continue;
	  
	  Double_t escale1=1;
	  if(doScaleCorr && isam==0) {
	    for(UInt_t ieta=0; ieta<escaleNbins; ieta++) {
	      if(fabs(tag->scEta)<escaleEta[ieta]) {
	        escale1 = escaleCorr[ieta];
		break;
	      }
	    }
	  }
	  
	  if(escale1*(tag->scEt) < PT_CUT)    continue;  // lepton pT cut
	  if(fabs(tag->scEta)    > ETA_CUT)   continue;  // lepton |eta| cut
	  if(!passEleID(tag,info->rhoLowEta)) continue;  // lepton selection
	  if(!(tag->hltMatchBits & trigObj))  continue;  // check trigger matching
	  
	  LorentzVector vTag(escale1*(tag->pt), tag->eta, tag->phi, ELE_MASS);
	  LorentzVector vTagSC(escale1*(tag->scEt), tag->scEta, tag->scPhi, ELE_MASS);
	
	  for(Int_t j=0; j<scArr->GetEntriesFast(); j++) {
	    const mithep::TPhoton *scProbe = (mithep::TPhoton*)((*scArr)[j]);
	    if(scProbe->scID == tag->scID) continue;
	    
	    // check ECAL gap
	    if(fabs(scProbe->scEta)>=ECAL_GAP_LOW && fabs(scProbe->scEta)<=ECAL_GAP_HIGH) continue;
	    
	   Double_t escale2=1;
	    if(doScaleCorr && isam==0) {
	      for(UInt_t ieta=0; ieta<escaleNbins; ieta++) {
	        if(fabs(scProbe->scEta)<escaleEta[ieta]) {
	          escale2 = escaleCorr[ieta];
		  break;
	        }
	      }
	    }
	    
	    if(escale2*(scProbe->pt) < PT_CUT)  continue;  // Supercluster ET cut ("pt" = corrected by PV position)
	    if(fabs(scProbe->scEta)  > ETA_CUT) continue;  // Supercluster |eta| cuts
	    
	    const mithep::TElectron *eleProbe=0;
	    Int_t iprobe=-1;
	    for(Int_t i2=0; i2<electronArr->GetEntriesFast(); i2++) {
	      if(i1==i2) continue;
	      const mithep::TElectron *ele = (mithep::TElectron*)((*electronArr)[i2]);
	      if(!(ele->typeBits & kEcalDriven)) continue;
	      if(scProbe->scID==ele->scID) { 
	        eleProbe = ele; 
		iprobe   = i2;
		break; 
	      }
            }
	    
	    LorentzVector vProbe((eleProbe) ? escale2*(eleProbe->pt) : escale2*(scProbe->pt), 
	                         (eleProbe) ? eleProbe->eta : scProbe->eta, 
				 (eleProbe) ? eleProbe->phi : scProbe->phi, 
				 ELE_MASS);
	    LorentzVector vProbeSC((eleProbe) ? escale2*(eleProbe->scEt) : escale2*(scProbe->pt), 
	                           scProbe->scEta, scProbe->scPhi, ELE_MASS);
	    
	    // mass window
	    LorentzVector vDilep = vTag + vProbe;
	    if((vDilep.M()<MASS_LOW) || (vDilep.M()>MASS_HIGH)) continue;
	    
	    // determine event category
	    UInt_t icat=0;
	    if(eleProbe) {
	      if(passEleID(eleProbe,info->rhoLowEta)) {
	        if(eleProbe->hltMatchBits & trigObj) {
		  if(i1>iprobe) continue;  // make sure we don't double count EleEle2HLT category
		  icat=eEleEle2HLT;
		
		} else {
		  icat=eEleEle1HLT;
		}	      
	      } else { 
	        icat=eEleEleNoSel;
	      } 
	    } else { 
	      icat=eEleSC;
	    }
	    if(icat==0) continue;
	    
	    
	    /******** We have a Z candidate! HURRAY! ********/
	    
	    nsel+=weight;
            nselvar+=weight*weight;
	    
	    // Perform matching of dileptons to GEN leptons from Z decay
	    Bool_t hasGenMatch = kFALSE;
	    if(isSignal) {
	      Bool_t match1 = ( (abs(gen->id_1)==EGenType::kElectron) && ((toolbox::deltaR(tag->eta, tag->phi, gen->eta_1, gen->phi_1) < 0.5)) )
	                      || ( (abs(gen->id_2)==EGenType::kElectron) && ((toolbox::deltaR(tag->eta, tag->phi, gen->eta_2, gen->phi_2) < 0.5)) );
	      Bool_t match2 = ( (abs(gen->id_1)==EGenType::kElectron) && ((toolbox::deltaR(vProbe.Eta(), vProbe.Phi(), gen->eta_1, gen->phi_1) < 0.5)) )
	                      || ( (abs(gen->id_2)==EGenType::kElectron) && ((toolbox::deltaR(vProbe.Eta(), vProbe.Phi(), gen->eta_2, gen->phi_2) < 0.5)) );
	      if(match1 && match2) hasGenMatch = kTRUE;
	    };
	    
	    //
	    // Fill tree
	    //
	    runNum   = info->runNum;
	    lumiSec  = info->lumiSec;
	    evtNum   = info->evtNum;
	    matchGen = hasGenMatch ? 1 : 0;
	    category = icat;
	    npv      = pvArr->GetEntriesFast();
	    npu      = info->nPU;
	    genVPt   = (hasGen) ? gen->vpt   : 0;
	    genVPhi  = (hasGen) ? gen->vphi  : 0;
	    genVy    = (hasGen) ? gen->vy    : 0;
	    genVMass = (hasGen) ? gen->vmass : 0;
	    scale1fb = weight;
	    met      = info->pfMET;
	    metPhi   = info->pfMETphi;
	    sumEt    = info->pfSumET;
	    
	    lep1 = &vTag;
	    q1   = tag->q;
	    
	    lep2 = &vProbe;
	    q2   = (eleProbe) ? eleProbe->q : -(tag->q);
	    
	    dilep = &vDilep;
	    
	    TVector2 vZPt((vDilep.Pt())*cos(vDilep.Phi()),(vDilep.Pt())*sin(vDilep.Phi()));        
            TVector2 vMet((info->pfMET)*cos(info->pfMETphi), (info->pfMET)*sin(info->pfMETphi));        
            TVector2 vU = -1.0*(vMet+vZPt);
            u1 = ((vDilep.Px())*(vU.Px()) + (vDilep.Py())*(vU.Py()))/(vDilep.Pt());  // u1 = (pT . u)/|pT|
            u2 = ((vDilep.Px())*(vU.Py()) - (vDilep.Py())*(vU.Px()))/(vDilep.Pt());  // u2 = (pT x u)/|pT|
	  
	    ///// electron specific /////
	    sc1        = &vTagSC;
	    trkIso1    = tag->trkIso03;
	    emIso1     = tag->emIso03;
	    hadIso1    = tag->hadIso03;
	    pfChIso1   = tag->pfChIso03;
	    pfGamIso1  = tag->pfGamIso03;	    
	    pfNeuIso1  = tag->pfNeuIso03;
	    pfCombIso1 = tag->pfChIso03 + TMath::Max(tag->pfNeuIso03 + tag->pfGamIso03 - (info->rhoLowEta)*getEffArea(tag->scEta), 0.);
	    sigieie1   = tag->sigiEtaiEta;
	    hovere1    = tag->HoverE;
	    eoverp1    = tag->EoverP;
	    fbrem1     = tag->fBrem;
	    dphi1      = tag->deltaPhiIn;
	    deta1      = tag->deltaEtaIn;
	    ecalE1     = tag->ecalE;
	    d01        = tag->d0;
	    dz1        = tag->dz;
	    isConv1    = tag->isConv;
	    nexphits1  = tag->nExpHitsInner;
	    typeBits1  = tag->typeBits;
	    
	    sc2        = &vProbeSC;
	    trkIso2    = (eleProbe) ? eleProbe->trkIso03      : -1;
	    emIso2     = (eleProbe) ? eleProbe->emIso03       : -1;
	    hadIso2    = (eleProbe) ? eleProbe->hadIso03      : -1;
	    pfChIso2   = (eleProbe) ? eleProbe->pfChIso03     : -1;
	    pfGamIso2  = (eleProbe) ? eleProbe->pfGamIso03    : -1;
	    pfNeuIso2  = (eleProbe) ? eleProbe->pfNeuIso03    : -1;
	    
	    pfCombIso2 = (eleProbe) ? 
	                 eleProbe->pfChIso03 + TMath::Max(eleProbe->pfNeuIso03 + eleProbe->pfGamIso03 - (info->rhoLowEta)*getEffArea(eleProbe->scEta), 0.) : 
			 -1;
	    
	    sigieie2   = (eleProbe) ? eleProbe->sigiEtaiEta   : scProbe->sigiEtaiEta;
	    hovere2    = (eleProbe) ? eleProbe->HoverE        : scProbe->HoverE;
	    eoverp2    = (eleProbe) ? eleProbe->EoverP        : -1;
	    fbrem2     = (eleProbe) ? eleProbe->fBrem         : -1;
	    dphi2      = (eleProbe) ? eleProbe->deltaPhiIn    : -999;
	    deta2      = (eleProbe) ? eleProbe->deltaEtaIn    : -999;
	    ecalE2     = (eleProbe) ? eleProbe->ecalE         : -999;
	    d02        = (eleProbe) ? eleProbe->d0            : -999;
	    dz2        = (eleProbe) ? eleProbe->dz            : -999;
	    isConv2    = (eleProbe) ? eleProbe->isConv        : 0;
	    nexphits2  = (eleProbe) ? eleProbe->nExpHitsInner : 0;
	    typeBits2  = (eleProbe) ? eleProbe->typeBits      : 0; 
	    
	    outTree->Fill();
	  }
        }
      }
      delete infile;
      infile=0, eventTree=0;    

      cout << nsel  << " +/- " << sqrt(nselvar);
      if(isam!=0) cout << " per 1/fb";
      cout << endl;
    }
    outFile->Write();
    outFile->Close(); 
  }
  delete info;
  delete gen;
  delete electronArr;
  delete scArr;
  delete pvArr;
  
    
  //--------------------------------------------------------------------------------------------------------------
  // Output
  //==============================================================================================================
   
  cout << "*" << endl;
  cout << "* SUMMARY" << endl;
  cout << "*--------------------------------------------------" << endl;
  cout << " Z -> e e" << endl;
  cout << "  Mass window: [" << MASS_LOW << ", " << MASS_HIGH << "]" << endl;
  cout << "  pT > " << PT_CUT << endl;
  cout << "  |eta| < " << ETA_CUT << endl;
  if(doScaleCorr)
    cout << "  *** Scale corrections applied ***" << endl;
  cout << endl;
  
  cout << endl;
  cout << "  <> Output saved in " << outputDir << "/" << endl;    
  cout << endl;  
      
  gBenchmark->Show("selectZee"); 
}