Exemple #1
0
void ToyEvent7::GenerateSignalKinematics(TRandom *rnd,Bool_t isData) {

   // fake decay of Z0 to two fermions
   double M0=91.1876;
   double Gamma=2.4952;
   // generated mass
   do {
      fMGen[2]=rnd->BreitWigner(M0,Gamma);
   } while(fMGen[2]<=0.0);

   double N_ETA=3.0;
   double MU_PT=5.;
   double SIGMA_PT=2.0;
   double DECAY_A=0.2;
   if(isData) {
      //N_ETA=2.5;
      MU_PT=6.;
      SIGMA_PT=1.8;
      //DECAY_A=0.5;
   }
   fEtaGen[2]=TMath::Power(rnd->Uniform(0,1.5),N_ETA);
   if(rnd->Uniform(-1.,1.)<0.) fEtaGen[2] *= -1.;
   fPhiGen[2]=rnd->Uniform(-M_PI,M_PI);
   do {
      fPtGen[2]=rnd->Landau(MU_PT,SIGMA_PT);
   } while((fPtGen[2]<=0.0)||(fPtGen[2]>500.));
   //========================== decay
   TLorentzVector sum;
   sum.SetPtEtaPhiM(fPtGen[2],fEtaGen[2],fPhiGen[2],fMGen[2]);
   // boost into lab-frame
   TVector3 boost=sum.BoostVector();
   // decay in rest-frame

   TLorentzVector p[3];
   double m=MASS1;
   double costh;
   do {
      double r=rnd->Uniform(-1.,1.);
      costh=r*(1.+DECAY_A*r*r);
   } while(fabs(costh)>=1.0);
   double phi=rnd->Uniform(-M_PI,M_PI);
   double e=0.5*sum.M();
   double ptot=TMath::Sqrt(e+m)*TMath::Sqrt(e-m);
   double pz=ptot*costh;
   double pt=TMath::Sqrt(ptot+pz)*TMath::Sqrt(ptot-pz);
   double px=pt*cos(phi);
   double py=pt*sin(phi);
   p[0].SetXYZT(px,py,pz,e);
   p[1].SetXYZT(-px,-py,-pz,e);
   for(int i=0;i<2;i++) {
      p[i].Boost(boost);
   }
   p[2]=p[0]+p[1];
   for(int i=0;i<3;i++) {
      fPtGen[i]=p[i].Pt();
      fEtaGen[i]=p[i].Eta();
      fPhiGen[i]=p[i].Phi();
      fMGen[i]=p[i].M();
   }
}
Exemple #2
0
inline TLorentzVector* kinematics::Boost( TLorentzVector* pa, TLorentzVector* pb, TLorentzVector* p )
{
	TLorentzVector pTmp = (*pa)+(*pb);
	TLorentzVector* pBoosted = (TLorentzVector*)p->Clone("");
	pBoosted->Boost(-1.*pTmp.BoostVector());
	return pBoosted;
}
Exemple #3
0
double CosThetaStar(TLorentzVector p1, TLorentzVector p2){
	TLorentzVector p = p1 + p2;
	TVector3 theBoost = p.BoostVector();
	TVector3 bostDir;
	if ( theBoost.Mag() != 0 ) bostDir = theBoost.Unit(); // / theBoost.Mag());
	else return -1;
	p1.Boost(-theBoost);
	if (p1.Vect().Mag()!=0) return p1.Vect().Dot(bostDir) / p1.Vect().Mag();
	else return -1;	
}
void Tran_to_fixed_target (TLorentzVector e_vec, TLorentzVector d_vec,
                            TLorentzVector &e_ft, TLorentzVector  &d_ft){
   //input: 
   //   e_vec - electron 4 vector in some frame
   //   d_vec - ion 4 vector in some frame
   //output:
   //   e_ft - electron 4 vector in rest frame of ion (fixed target frame)
   //   d_ft - ion 4 vector in its rest frame 
   e_ft = e_vec;
   d_ft = d_vec;
   
   d_ft.Boost(-d_vec.BoostVector()); //should be (0,0,0, mass)
   e_ft.Boost(-d_vec.BoostVector());
   return;


}
Exemple #5
0
inline float kinematics::cosThetaBoost( TLorentzVector* pa, float ca,
										TLorentzVector* pb, float cb )
{
	// http://xrootd.slac.stanford.edu/BFROOT/www/doc/workbook_backup_010108/analysis/analysis.html
	// A useful quantity in many analyses is the helicity angle.
	// In the reaction Y -> X -> a + b, the helicity angle of 
	// particle a is the angle measured in the rest frame of the
	//decaying parent particle, X, between the direction of the
	// decay daughter a and the direction of the grandparent particle Y.

	TLorentzVector pTmp = (*pa)+(*pb); // this is the mumu system (Z) 4vector
	TVector3 ZboostVector = pTmp.BoostVector(); // this is the 3vector of the Z
	TLorentzVector p; // this is the muon 4vector
	
	if(ca<0)      p.SetPxPyPzE(pa->Px(),pa->Py(),pa->Pz(),pa->E());
	else if(cb<0) p.SetPxPyPzE(pb->Px(),pb->Py(),pb->Pz(),pb->E());
	p.Boost( -ZboostVector ); // boost p to the dimuon CM (rest) frame
	float cosThetaB = p.Vect()*pTmp.Vect()/(p.P()*pTmp.P());
	//if (ySystem(pa,pb) < 0) cosThetaB *= -1.; // reclassify ???
	return cosThetaB;
}
Exemple #6
0
////////////////////////////////////////////////////////////////////////
// Calculates theta and phi in HX frame
////////////////////////////////////////////////////////////////////////
pair<double, double> GetAngles_HX( TLorentzVector a,  TLorentzVector b) {
	TLorentzVector c = a+b;                   // JPsi momentum in lab frame
	TVector3 bv = c.BoostVector();
	TLorentzVector p1(0., 0.,  1380., 1380.); // beam momentum in lab frame
	TLorentzVector p2(0., 0., -1380., 1380.); // beam momentum in lab frame
	p1.Boost(-bv);
	p2.Boost(-bv);
	TVector3 beam1 = p1.Vect().Unit();        // beam direction in JPsi rest frame
	TVector3 beam2 = p2.Vect().Unit();        // beam direction in JPsi rest frame

	TVector3 Z = c.Vect().Unit();             // JPsi direction in lab frame
	TVector3 Y = beam1.Cross( beam2 ).Unit(); // the production plane normal
	TVector3 X = Y.Cross(Z).Unit();           // completes the right-handed coordinate

	a.Boost(-bv);                             // muon+ momentum in JPsi rest frame
	TVector3 mu(a.Vect().Dot(X), a.Vect().Dot(Y), a.Vect().Dot(Z)); // transform to new coordinate
	pair<double, double> angles;
	angles.first = mu.Theta();
	angles.second = mu.Phi()>0. ? mu.Phi() : mu.Phi()+2.*TMath::Pi();
	return angles;
}
void analysis_pbarp_Xi_test(int nevts=0){
  
  TDatabasePDG::Instance()-> AddParticle("pbarpSystem","pbarpSystem", 1.9, kFALSE, 0.1, 0,"", 88888);
  
  TStopwatch timer; 



  //Output File
  TString Path = "/private/puetz/mysimulations/analysis/pbarp_Xiplus_Ximinus/idealtracking/10000_events/";
  TString outPath = Path;
  TString OutputFile = outPath + "analysis_output_test.root";
  
  //Input simulation Files
  TString inPIDFile = Path + "pid_complete.root";
  TString inParFile = Path + "simparams.root";
  TString PIDParFile = TString( gSystem->Getenv("VMCWORKDIR")) + "/macro/params/all.par";
  
  //Initialization
  FairLogger::GetLogger()->SetLogToFile(kFALSE);
  FairRunAna* RunAna = new FairRunAna();
  FairRuntimeDb* rtdb = RunAna->GetRuntimeDb();
  RunAna->SetInputFile(inPIDFile);
  
  //setup parameter database
  FairParRootFileIo* parIo = new FairParRootFileIo();
  parIo->open(inParFile);
  FairParAsciiFileIo* parIoPID = new FairParAsciiFileIo();
  parIoPID->open(PIDParFile.Data(),"in");
  
  rtdb->setFirstInput(parIo);
  rtdb->setSecondInput(parIoPID);
  rtdb->setOutput(parIo);

  RunAna->SetOutputFile(OutputFile);
  RunAna->Init();

  //*** create tuples
  RhoTuple * ntpMC = new RhoTuple("ntpMC", "MCTruth info");
  RhoTuple * ntpPiMinus = new RhoTuple("ntpPiMinus", "PiMinus info");
  RhoTuple * ntpPiPlus = new RhoTuple("ntpPiPlus", "PiPlus info");
  RhoTuple * ntpProton = new RhoTuple("ntpProton", "Proton info");
  RhoTuple * ntpAntiProton = new RhoTuple("ntpAntiProton", "Antiproton info");
  RhoTuple * ntpLambda0 = new RhoTuple("ntpLambda0", "Lambda0 info");
  RhoTuple * ntpAntiLambda0 = new RhoTuple("ntpAntiLambda0", "AntiLambda0 info");
  RhoTuple * ntpXiMinus = new RhoTuple("ntpXiMinus", "XiMinus info");
  RhoTuple * ntpXiPlus = new RhoTuple("ntpXiPlus", "XiPlus info");
  RhoTuple * ntpXiSys = new RhoTuple("ntpXiSys", "XiMinus XiPlus system info");

  //Create output file 
  TFile *out = TFile::Open(outPath+"output_ana_test.root","RECREATE");

  // data reader Object
  PndAnalysis* theAnalysis = new PndAnalysis();
  if (nevts==0) nevts = theAnalysis->GetEntries();
  
  //RhoCandLists for analysis
  RhoCandList piplus, piminus, lambda0, antiLambda0, proton, antiProton, xiplus, ximinus, xiSys;
  RhoCandList NotCombinedPiMinus, CombinedPiMinus, CombinedPiPlus, NotCombinedPiPlus;
  RhoCandList SelectedProton, SelectedAntiProton, SelectedPiMinus, SelectedPiPlus;
  RhoCandList Lambda0Fit, AntiLambda0Fit, XiMinusFit, XiPlusFit;
  RhoCandList mclist, all;

  //Dummy RhoCandidate
  RhoCandidate * dummyCand = new RhoCandidate();


  //***Mass selector
  double m0_lambda0= TDatabasePDG::Instance()->GetParticle("Lambda0")->Mass();
  cout<<"Mass of Lambda0: "<<m0_lambda0<<endl;
  RhoMassParticleSelector * lambdaMassSelector = new RhoMassParticleSelector("lambda0", m0_lambda0, 0.3);
 
  double m0_Xi = TDatabasePDG::Instance()->GetParticle("Xi-")->Mass();
  cout<<"Mass of Xi-: "<<m0_Xi<<endl;
  RhoMassParticleSelector * xiMassSelector = new RhoMassParticleSelector("Xi-", m0_Xi, 0.3);

  double m0_pbarpsystem = TDatabasePDG::Instance()->GetParticle("pbarpSystem")->Mass();

  
  double pbarmom = 2.7;
  double p_m0 = TDatabasePDG::Instance()->GetParticle("proton")->Mass();
  TLorentzVector ini (0,0, pbarmom, sqrt(p_m0*p_m0+ pbarmom*pbarmom)+p_m0);
  TVector3 beamBoost = ini.BoostVector();
  
  PndRhoTupleQA qa(theAnalysis, pbarmom);
 
  int evt=-1;
  int index=0;

  while (theAnalysis->GetEvent() && ++evt<nevts){

    if ((evt%100)==0) cout << "evt "<< evt <<endl;
    cout << "Running event " << evt << endl;
		
    //***get MC list and store info
    theAnalysis->FillList(mclist, "McTruth");
    qa.qaMcList("", mclist, ntpMC);
    ntpMC->DumpData();
   	
		
	//if you want to print the hole MCTree uncomment the following
    /*
    for (int j=0;j<mclist.GetLength();++j)
    {
      RhoCandidate *mcmother = mclist[j]->TheMother();        // mother of mc particle         
      int muid = (mcmother==0x0) ? -1 : mcmother->GetTrackNumber(); // track ID of mother, if existing 
        
      cout << "Track "<< mclist[j]->GetTrackNumber()<<" (PDG:"<<mclist[j]->PdgCode() <<") has mother "<<muid;
      if (mclist[j]->NDaughters()>0) cout <<" and daughter(s) ";
	 for (k=0;k<mclist[j]->NDaughters();++k) cout <<mclist[j]->Daughter(k)->GetTrackNumber()<<"  ";
	cout<<endl;        
    }*/


    //***Setup event shape object
		
    TString PidSelection = "PidAlgoIdealCharged";//"PidAlgoMvd;PidAlgoStt;PidAlgoDrc";

    theAnalysis->FillList(all, "All", PidSelection);
    PndEventShape evsh(all, ini, 0.05, 0.1);
    
    //***Selection with no PID info
    theAnalysis->FillList(piminus, "PionAllMinus", PidSelection);
//    theAnalysis->FillList(NotCombinedPiMinus, "PionAllMinus", PidSelection);
//    theAnalysis->FillList(NotCombinedPiPlus, "PionAllPlus", PidSelection);
    theAnalysis->FillList(piplus, "PionAllPlus", PidSelection);
    theAnalysis->FillList(proton, "ProtonAllPlus", PidSelection);
    theAnalysis->FillList(antiProton, "ProtonAllMinus", PidSelection);



    for (int pip=0; pip<piplus.GetLength(); ++pip){
        ntpPiPlus->Column("ev",     (Float_t) evt);
        ntpPiPlus->Column("cand",    (Float_t) pip);
        ntpPiPlus->Column("ncand",   (Float_t) piplus.GetLength());
        ntpPiPlus->Column("McTruthMatch", (bool) theAnalysis->McTruthMatch(piplus[pip]));


        qa.qaP4("PiPlus_", piplus[pip]->P4(), ntpPiPlus);
        qa.qaCand("PiPlus_", piplus[pip], ntpPiPlus);

        jenny::numberOfHitsInSubdetector("PiPlus_", piplus[pip], ntpPiPlus);
        jenny::tagNHits("PiPlus_", piplus[pip], ntpPiPlus);
        int tag = jenny::tagHits(piplus[pip]);


        RhoCandidate * mother_pip = piplus[pip]->GetMcTruth()->TheMother();
        int moth_pip = (0x0==mother_pip)? 88888 : mother_pip->PdgCode();

        ntpPiPlus->Column("Mother", (Float_t) moth_pip);
        ntpPiPlus->Column("PiPlus_CosTheta", (Float_t) piplus[pip]->GetMomentum().CosTheta());

        qa.qaP4("PiPlus_MC_", piplus[pip]->GetMcTruth()->P4(), ntpPiPlus);
        qa.qaCand("PiPlus_MC_", piplus[pip]->GetMcTruth(), ntpPiPlus);
        ntpPiPlus->Column("PiPlus_MC_CosTheta", (Float_t) piplus[pip]->GetMcTruth()->GetMomentum().CosTheta());

        if(tag==1){
        	SelectedPiPlus.Append(piplus[pip]);
        	NotCombinedPiPlus.Append(piplus[pip]);
        }

        ntpPiPlus->DumpData();
    }

    for (int pim=0; pim<piminus.GetLength(); ++pim){
        ntpPiMinus->Column("ev",     (Float_t) evt);
        ntpPiMinus->Column("cand",    (Float_t) pim);
        ntpPiMinus->Column("ncand",   (Float_t) piminus.GetLength());
        ntpPiMinus->Column("McTruthMatch", (bool) theAnalysis->McTruthMatch(piminus[pim]));

        qa.qaP4("piminus_", piminus[pim]->P4(), ntpPiMinus);
        qa.qaCand("piminus_", piminus[pim], ntpPiMinus);

        jenny::numberOfHitsInSubdetector("piminus_", piminus[pim], ntpPiMinus);
        jenny::tagNHits("piminus_", piminus[pim], ntpPiMinus);
        int tag = jenny::tagHits(piminus[pim]);

        RhoCandidate * mother_pim = piminus[pim]->GetMcTruth()->TheMother();
        int moth_pim = (0x0==mother_pim)? 88888 : mother_pim->PdgCode();

        ntpPiMinus->Column("Mother", (Float_t) moth_pim);
        ntpPiMinus->Column("PiMinus_CosTheta", (Float_t) piminus[pim]->GetMomentum().CosTheta());

        qa.qaP4("piminus_MC_", piminus[pim]->GetMcTruth()->P4(), ntpPiMinus);
        qa.qaCand("piminus_MC_", piminus[pim]->GetMcTruth(), ntpPiMinus);
        ntpPiMinus->Column("piminus_MC_CosTheta", (Float_t) piminus[pim]->GetMcTruth()->GetMomentum().CosTheta());

        ntpPiMinus->DumpData();

        if(tag==1){
        	SelectedPiMinus.Append(piminus[pim]);
        	NotCombinedPiMinus.Append(piminus[pim]);
        }
    }

    for (int prot=0; prot<proton.GetLength(); ++prot){
        ntpProton->Column("ev",     (Float_t) evt);
        ntpProton->Column("cand",    (Float_t) prot);
        ntpProton->Column("ncand",   (Float_t) proton.GetLength());
        ntpProton->Column("McTruthMatch", (bool) theAnalysis->McTruthMatch(proton[prot]));

        qa.qaP4("proton_", proton[prot]->P4(), ntpProton);
        qa.qaCand("proton_", proton[prot], ntpProton);

        jenny::numberOfHitsInSubdetector("proton_", proton[prot], ntpProton);
//        jenny::tagNHits("proton_", proton[prot], ntpProton);

        int tag = jenny::tagHits(proton[prot]);

        RhoCandidate * mother_prot = proton[prot]->GetMcTruth()->TheMother();
        int moth_prot = (0x0==mother_prot)? 88888 : mother_prot->PdgCode();

        ntpProton->Column("Mother", (Float_t) moth_prot);
        ntpProton->Column("proton_CosTheta", (Float_t) proton[prot]->GetMomentum().CosTheta());

        qa.qaP4("proton_MC_", proton[prot]->GetMcTruth()->P4(), ntpProton);
        qa.qaCand("proton_", proton[prot]->GetMcTruth(), ntpProton);
        ntpProton->Column("proton_MC_CosTheta", (Float_t) proton[prot]->GetMcTruth()->GetMomentum().CosTheta());

        ntpProton->DumpData();

        if(tag==1) SelectedProton.Append(proton[prot]);

    }

    for (int aProt=0; aProt<antiProton.GetLength(); ++aProt){
        ntpAntiProton->Column("ev",     (Float_t) evt);
        ntpAntiProton->Column("cand",    (Float_t) aProt);
        ntpAntiProton->Column("ncand",   (Float_t) antiProton.GetLength());
        ntpAntiProton->Column("McTruthMatch", (bool) theAnalysis->McTruthMatch(antiProton[aProt]));

        qa.qaP4("antiProton_", antiProton[aProt]->P4(), ntpAntiProton);
        qa.qaCand("antiProton_", antiProton[aProt], ntpAntiProton);

        jenny::numberOfHitsInSubdetector("antiProton_", antiProton[aProt], ntpAntiProton);
//        jenny::tagNHits("antiProton_", antiProton[aProt], ntpAntiProton);
        int tag = jenny::tagHits(antiProton[aProt]);

        RhoCandidate * mother_aProt = antiProton[aProt]->GetMcTruth()->TheMother();
        int moth_aProt = (0x0==mother_aProt)? 88888 : mother_aProt->PdgCode();

        ntpAntiProton->Column("Mother", (Float_t) moth_aProt);
        ntpAntiProton->Column("antiProton_CosTheta", (Float_t) antiProton[aProt]->GetMomentum().CosTheta());


        qa.qaP4("antiProton_MC_", antiProton[aProt]->GetMcTruth()->P4(), ntpAntiProton);
        qa.qaCand("antiProton_", antiProton[aProt]->GetMcTruth(), ntpAntiProton);
        ntpAntiProton->Column("antiProton_MC_CosTheta", (Float_t) antiProton[aProt]->GetMcTruth()->GetMomentum().CosTheta());

        ntpAntiProton->DumpData();

        if(tag==1) SelectedAntiProton.Append(antiProton[aProt]);
    }





    //***Lambda0 -> PiMinus + Proton

    lambda0.Combine(SelectedPiMinus,SelectedProton);
	lambda0.Select(lambdaMassSelector);
    lambda0.SetType(kl0);

    std::map<int,int> bestVtxFitLambda0, bestMassFitLambda0;

    bestVtxFitLambda0 = jenny::VertexQaIndex(&lambda0);
    bestMassFitLambda0 = jenny::MassFitQaIndex(&lambda0, m0_lambda0);


    for (int j=0; j<lambda0.GetLength(); ++j){


      //general info about event
      ntpLambda0->Column("ev",     (Float_t) evt);
      ntpLambda0->Column("cand",    (Float_t) j);
      ntpLambda0->Column("ncand",   (Float_t) lambda0.GetLength());
      ntpLambda0->Column("McTruthMatch", (bool) theAnalysis->McTruthMatch(lambda0[j]));
      ntpLambda0->Column("Lambda0_Pdg", (Float_t) lambda0[j]->PdgCode());

	  RhoCandidate * mother = lambda0[j]->TheMother();
  	  int moth = (mother==0x0) ? 88888 : mother->PdgCode();

	  ntpLambda0->Column("Mother", (Float_t) moth);

      qa.qaP4("Lambda0_", lambda0[j]->P4(), ntpLambda0);
      qa.qaComp("Lambda0_", lambda0[j], ntpLambda0);


      // do vertex fit
      PndKinVtxFitter vertexfitterLambda0 (lambda0[j]);
	  vertexfitterLambda0.Fit();
      RhoCandidate * lambda0Fit = lambda0[j]->GetFit();


      // store info of vertex fit
      qa.qaFitter("VtxFit_", &vertexfitterLambda0, ntpLambda0);
      ntpLambda0->Column("VtxFit_HowGood", (Int_t) bestVtxFitLambda0[j]);
      qa.qaVtx("VtxFit_", lambda0Fit, ntpLambda0);

      // differenz to MCTruth
       qa.qaMcDiff("fvtxMcDiff_", lambda0Fit, ntpLambda0);


      // do mass fit
      PndKinFitter massFitterLambda0(lambda0Fit);
      massFitterLambda0.AddMassConstraint(m0_lambda0);
      massFitterLambda0.Fit();

      RhoCandidate * lambda0Fit_mass = lambda0Fit->GetFit();
      qa.qaFitter("MassFit_", &massFitterLambda0, ntpLambda0);

      ntpLambda0->Column("MassFit_HowGood", (Int_t) bestMassFitLambda0[j]);


      RhoCandidate * truth = lambda0[j]->GetMcTruth();
      RhoCandidate * truthDaughter = lambda0[j]->Daughter(0)->GetMcTruth();
      TLorentzVector l;
      TVector3 dl;

	    if(0x0 != truth){
	    	l = truth->P4();
	    	qa.qaVtx("McTruth_", truth, ntpLambda0);
	    	dl = truth->Daughter(0)->Pos();
	    }
	    else{
	    	qa.qaVtx("McTruth_", dummyCand, ntpLambda0);
	    }

      jenny::qaP3("McTruth_", dl, ntpLambda0);
      qa.qaP4("McTruth_", l, ntpLambda0);


      //*** use for Xi only bestChi2Cand

      if (bestVtxFitLambda0[j]==1 && bestMassFitLambda0[j]>0){
		  Lambda0Fit.Append(lambda0Fit);
		  jenny::CombinedList(lambda0Fit, &CombinedPiMinus, -211);
      }


      //***information of boosted particle
      lambda0Fit->Boost(-beamBoost);
      qa.qaComp("boost_", lambda0Fit, ntpLambda0);

      ntpLambda0->DumpData();


   }

    jenny::GetNotCombinedList(CombinedPiMinus, &NotCombinedPiMinus);


//     Lambda0Fit.Cleanup();
     CombinedPiMinus.Cleanup();
     SelectedPiMinus.Cleanup();
     SelectedProton.Cleanup();
//     NotCombinedPiMinus.Cleanup();
     bestVtxFitLambda0.clear();
     bestMassFitLambda0.clear();


    //***AntiLambda0 -> PiPlus + AntiProton
    antiLambda0.Combine(SelectedPiPlus,SelectedAntiProton);
	antiLambda0.Select(lambdaMassSelector);
    antiLambda0.SetType(kal0);

    std::map<int,int> bestVtxFitAntiLambda0, bestMassFitAntiLambda0;

    bestVtxFitAntiLambda0 = jenny::VertexQaIndex(&antiLambda0);
    bestMassFitAntiLambda0 = jenny::MassFitQaIndex(&antiLambda0, m0_lambda0);


    for (int j=0; j<antiLambda0.GetLength(); ++j){

      //general info about event
      ntpAntiLambda0->Column("ev",     (Float_t) evt);
      ntpAntiLambda0->Column("cand",    (Float_t) j);
      ntpAntiLambda0->Column("ncand",   (Float_t) antiLambda0.GetLength());
      ntpAntiLambda0->Column("McTruthMatch", (bool) theAnalysis->McTruthMatch(antiLambda0[j]));
      ntpAntiLambda0->Column("AntiLambda0_Pdg", (Float_t) antiLambda0[j]->PdgCode());

	  RhoCandidate * mother = antiLambda0[j]->TheMother();
	  int moth = (mother==0x0) ? 88888 : mother->PdgCode();
	  ntpAntiLambda0->Column("Mother", (Float_t) moth);

      qa.qaP4("AntiLambda0_", antiLambda0[j]->P4(), ntpAntiLambda0);
      qa.qaComp("AntiLambda0_", antiLambda0[j], ntpAntiLambda0);


      // do vertex fit
      PndKinVtxFitter vertexfitterAntiLambda0 (antiLambda0[j]);
      vertexfitterAntiLambda0.Fit();
      RhoCandidate * antiLambda0Fit = antiLambda0[j]->GetFit();



      // store info of vertex fit
      qa.qaFitter("VtxFit_", &vertexfitterAntiLambda0, ntpAntiLambda0);
      qa.qaVtx("VtxFit_", antiLambda0Fit, ntpAntiLambda0);

      ntpAntiLambda0->Column("VtxFit_HowGood", (Int_t) bestVtxFitAntiLambda0[j]);


      // do mass fit
      PndKinFitter massFitterAntiLambda0(antiLambda0Fit);
      massFitterAntiLambda0.AddMassConstraint(m0_lambda0);
      massFitterAntiLambda0.Fit();

      RhoCandidate * antiLambda0Fit_mass = antiLambda0Fit->GetFit();
      qa.qaFitter("MassFit_", &massFitterAntiLambda0, ntpAntiLambda0);
      ntpAntiLambda0->Column("MassFit_HowGood", (Int_t) bestMassFitAntiLambda0[j]);


      RhoCandidate * truth = antiLambda0[j]->GetMcTruth();

      TLorentzVector l;
      if(0x0 != truth){
				l = truth->P4();
				qa.qaVtx("MCTruth_", truth, ntpAntiLambda0);
      }
      else{
    	  qa.qaVtx("McTruth_", dummyCand, ntpAntiLambda0);
      }

      qa.qaP4("MCTruth_", l, ntpAntiLambda0);


      //***information of boosted particle
      antiLambda0Fit->Boost(-beamBoost);
      qa.qaComp("boost_", antiLambda0Fit, ntpAntiLambda0);



      if(bestVtxFitAntiLambda0[j]==1 && bestMassFitAntiLambda0[j]>0){
		  AntiLambda0Fit.Append(antiLambda0Fit);
		  jenny::CombinedList(antiLambda0Fit, &CombinedPiPlus, 211);
      }

      ntpAntiLambda0->DumpData();
    }

    jenny::GetNotCombinedList(CombinedPiPlus, &NotCombinedPiPlus);

	CombinedPiPlus.Cleanup();
	SelectedPiPlus.Cleanup();
	SelectedAntiProton.Cleanup();

    bestVtxFitAntiLambda0.clear();
    bestMassFitAntiLambda0.clear();



    //*** Xi- -> Lambda0 + Pi-
	ximinus.Combine(Lambda0Fit, NotCombinedPiMinus);
	ximinus.Select(xiMassSelector);
	ximinus.SetType(kXim);

	std::map<int,int> BestVtxFitXiMinus, BestMassFitXiMinus;

	BestVtxFitXiMinus = jenny::VertexQaIndex(&ximinus);
	BestMassFitXiMinus = jenny::MassFitQaIndex(&ximinus, m0_Xi);


    for (int j=0; j<ximinus.GetLength(); ++j){

      //general info about event
      ntpXiMinus->Column("ev",     (Float_t) evt);
      ntpXiMinus->Column("cand",    (Float_t) j);
      ntpXiMinus->Column("ncand",   (Float_t) ximinus.GetLength());
      ntpXiMinus->Column("McTruthMatch", (bool) theAnalysis->McTruthMatch(ximinus[j]));
      ntpXiMinus->Column("XiMinus_Pdg", (Float_t) ximinus[j]->PdgCode());


	  RhoCandidate * mother = ximinus[j]->TheMother();
	  int moth = (mother==0x0) ? 88888 : mother->PdgCode();
	  ntpXiMinus->Column("Mother", (Float_t) moth);

      qa.qaP4("XiMinus_", ximinus[j]->P4(), ntpXiMinus);
      qa.qaComp("XiMinus_", ximinus[j], ntpXiMinus);
      qa.qaPoca("XiMinus_", ximinus[j], ntpXiMinus);



      // do vertex-fit

      PndKinVtxFitter vertexfitterXiMinus (ximinus[j]);
      vertexfitterXiMinus.Fit();
      RhoCandidate * ximinusFit = ximinus[j]->GetFit();


      // store info of vertex-fit

      qa.qaFitter("VtxFit_", &vertexfitterXiMinus, ntpXiMinus);
      ntpXiMinus->Column("VtxFit_HowGood", (Int_t) BestVtxFitXiMinus[j]);

      qa.qaVtx("VtxFit_", ximinusFit, ntpXiMinus);
//      qa.Cand("VtxFit_", ximinusFit, ntpXiMinus);


	  // difference to MCTruth
      qa.qaMcDiff("VtxFit_", ximinusFit, ntpXiMinus);




      // do mass fit
      PndKinFitter massFitterXiMinus(ximinusFit);
      massFitterXiMinus.AddMassConstraint(m0_lambda0);
      massFitterXiMinus.Fit();

      RhoCandidate * ximinusFit_mass = ximinusFit->GetFit();
      qa.qaFitter("MassFit_", &massFitterXiMinus, ntpXiMinus);
      ntpXiMinus->Column("MassFit_HowGood", (Int_t) BestMassFitXiMinus[j]);

      qa.qaMcDiff("MassFit_", ximinusFit_mass, ntpXiMinus);


      RhoCandidate * truth = ximinus[j]->GetMcTruth();
      TLorentzVector l;

      if(0x0 != truth){
				l = truth->P4();
				qa.qaVtx("MCTruth_", truth, ntpXiMinus);
      }
      else{
    	  qa.qaVtx("MCTruth_", dummyCand, ntpXiMinus);
      }

      qa.qaP4("MCTruth_", l, ntpXiMinus);

      if (BestVtxFitXiMinus[j]==1 && BestMassFitXiMinus[j]>0){
    	  XiMinusFit.Append(ximinusFit);
      }


      //***information of boosted particle
      ximinusFit->Boost(-beamBoost);
      qa.qaComp("boost_", ximinusFit, ntpXiMinus);

      ntpXiMinus->DumpData();


	}
    Lambda0Fit.Cleanup();
    NotCombinedPiMinus.Cleanup();

	BestVtxFitXiMinus.clear();
	BestMassFitXiMinus.clear();



	//*** Xi+ -> AntiLambda0 + Pi+
	xiplus.Combine(AntiLambda0Fit,piplus);
	xiplus.Select(xiMassSelector);
	xiplus.SetType(kaXip);

	std::map<int,int> BestVtxFitXiPlus, BestMassFitXiPlus;

	BestVtxFitXiPlus = jenny::VertexQaIndex(&xiplus);
	BestMassFitXiPlus = jenny::MassFitQaIndex(&xiplus, m0_Xi);

    for (int j=0; j<xiplus.GetLength(); ++j){

      //general info about event
      ntpXiPlus->Column("ev",     (Float_t) evt);
      ntpXiPlus->Column("cand",    (Float_t) j);
      ntpXiPlus->Column("ncand",   (Float_t) xiplus.GetLength());
      ntpXiPlus->Column("McTruthMatch", (bool) theAnalysis->McTruthMatch(xiplus[j]));

      RhoCandidate * mother = xiplus[j]->TheMother();
      int moth = (mother==0x0) ? 88888 : mother->PdgCode();
      ntpXiPlus->Column("Mother", (Float_t) moth);

      qa.qaP4("Xiplus_", xiplus[j]->P4(), ntpXiPlus);
      qa.qaComp("Xiplus_", xiplus[j], ntpXiPlus);


//      int tag = 0;
//      int dtag[2] = {0,0};
//
//      for (int dau=0; dau<xiplus[j]->NDaughters(); dau++){
//
//    	  RhoCandidate * daughter = xiplus[j]->Daughter(dau);
//    	  if(daughter->IsComposite()){
//    		  int dtag1 = jenny::tagHits(daughter->Daughter(0));
//    		  int dtag2 = jenny::tagHits(daughter->Daughter(1));
//       		  if(dtag1==1 && dtag2==1) dtag[dau]=1;
//    	  }
//    	  else{
//    		  dtag[dau] = jenny::tagHits(daughter);
//    	  }
//	 }
//
//      if(dtag[0]==1 && dtag[1]==1) tag=1;
//
//      ntpXiPlus->Column("XiPlus_HitTag", (Int_t) tag);



      //******** do vertex-fit
      PndKinVtxFitter vertexfitterxiplus (xiplus[j]);
      vertexfitterxiplus.Fit();
      RhoCandidate * xiplusFit = xiplus[j]->GetFit();


      // store info of vertex-fit
      qa.qaFitter("VtxFit_", &vertexfitterxiplus, ntpXiPlus);
      ntpXiPlus->Column("VtxFit_HowGood", (Int_t) BestVtxFitXiPlus[j]);
      qa.qaVtx("VtxFit_", xiplusFit, ntpXiPlus);

	  // difference to MCTruth
      qa.qaMcDiff("VtxFit_", xiplusFit, ntpXiPlus);


      //****** do mass fit
      PndKinFitter massFitterxiplus(xiplusFit);
      massFitterxiplus.AddMassConstraint(m0_lambda0);
      massFitterxiplus.Fit();

      RhoCandidate * xiplusFit_mass = xiplusFit->GetFit();
      qa.qaFitter("MassFit_", &massFitterxiplus, ntpXiPlus);
      ntpXiPlus->Column("MassFit_HowGood", (float) BestMassFitXiPlus[j]);
      qa.qaVtx("MassFit_", xiplusFit_mass, ntpXiPlus);

      qa.qaMcDiff("MassFit_", xiplusFit_mass, ntpXiPlus);

      RhoCandidate * truth = xiplus[j]->GetMcTruth();
      TLorentzVector l;
      if(0x0 != truth){
				l = truth->P4();
				qa.qaVtx("MCTruth_", truth, ntpXiPlus);
      }
      else{
    	  qa.qaVtx("MCTruth_", dummyCand, ntpXiPlus);
      }

      qa.qaP4("MCTruth_", l, ntpXiPlus);


      if(BestVtxFitXiPlus[j]==1 && BestMassFitXiPlus[j]>0){
    	  XiPlusFit.Append(xiplusFit);
      }

      //***information of boosted particle
      xiplusFit->Boost(-beamBoost);
      qa.qaComp("boost_", xiplusFit, ntpXiPlus);

      ntpXiPlus->DumpData();
	 }

    AntiLambda0Fit.Cleanup();
//    BestCandAntiLambda0.Cleanup();
	BestVtxFitXiPlus.clear();
	BestMassFitXiPlus.clear();



    //******* Xi+ Xi- System*****************************

    xiSys.Combine(XiPlusFit, XiMinusFit);
    xiSys.SetType(88888);

    for (int syscand=0; syscand<xiSys.GetLength(); ++syscand){

		ntpXiSys->Column("ev",     (Float_t) evt);
		ntpXiSys->Column("cand",    (Float_t) j);
		ntpXiSys->Column("ncand",   (Float_t) ximinus.GetLength());
		ntpXiSys->Column("McTruthMatch", (bool) theAnalysis->McTruthMatch(xiSys[syscand]));

		RhoCandidate * mother = xiSys[syscand]->TheMother();
		int moth = (mother==0x0) ? 88888 : mother->PdgCode();
		ntpXiSys->Column("Mother", (Float_t) moth);

		qa.qaP4("XiSys_", xiSys[syscand]->P4(), ntpXiSys);
		qa.qaComp("XiSys_", xiSys[syscand], ntpXiSys);
		qa.qaPoca("XiSys_", xiSys[syscand], ntpXiSys);


		RhoCandidate *  truth = xiSys[syscand]->GetMcTruth();
		TLorentzVector l;

		if (truth != 0x0){
//			qa.qaComp("McTruth_", truth, ntpXiSys);
			qa.qaVtx("McTruth_", truth, ntpXiSys);
			l = truth->P4();
		}
		else{
//			qa.qaComp("McTruth_", dummyCand, ntpXiSys);
			qa.qaVtx("McTruth_", dummyCand, ntpXiSys);
		}
		qa.qaP4("McTruth_", l, ntpXiSys);


		//4C-Fitter

		PndKinFitter fitter4c (xiSys[syscand]);
		fitter4c.Add4MomConstraint(ini);
		fitter4c.Fit();

		RhoCandidate * xiSysFit4c = xiSys[syscand]->GetFit();

		qa.qaFitter("4CFit_", &fitter4c, ntpXiSys);
		qa.qaComp("4cFit_", xiSysFit4c, ntpXiSys);
		qa.qaVtx("4CFit_", xiSysFit4c, ntpXiSys);


		ntpXiSys->DumpData();


    }
    XiMinusFit.Cleanup();
    XiPlusFit.Cleanup();
  }



   

  //Write output
  out->cd();

  ntpMC -> GetInternalTree()->Write();
  ntpPiMinus ->GetInternalTree()->Write();
  ntpPiPlus->GetInternalTree()->Write();
  ntpProton->GetInternalTree()->Write();
  ntpAntiProton->GetInternalTree()->Write();
  ntpLambda0->GetInternalTree()->Write();
  ntpAntiLambda0->GetInternalTree()->Write();
  ntpXiMinus->GetInternalTree()->Write();
  ntpXiPlus->GetInternalTree()->Write();
  ntpXiSys->GetInternalTree()->Write();

  out->Save();
  

  timer.Stop();
  Double_t rtime = timer.RealTime();
  Double_t ctime = timer.CpuTime();
  cout<<endl<<endl;
  cout<<"Macro finisched successfully."<<endl;
  cout<<"Realtime: "<<rtime<<" s, CPU time: "<<ctime<<" s"<<endl;
  cout<<endl;

 
  exit(0);
 
}
Exemple #8
0
{
  gSystem.Load("libPhysics");
  TLorentzVector lab(0.17,0.32,4.84,4.938);
  TLorentzVector zero(0.0,0.0,0.0,0.0);

  cout << "LAB = "<< lab[0]<< ", "<< lab[1]<< ", " << lab[2]<< ", " << lab[3]
       << ", rho = " << lab.Rho()<< ", theta = "<< lab.Theta()
       << ", phi = "<< lab.Phi()<< endl;

  TLorentzVector W = lab+zero;
  lab.Boost(-W.BoostVector());

  cout << "CM = "<< lab[0]<< ", "<< lab[1]<< ", " << lab[2]<< ", " << lab[3]
       << ", rho = " << lab.Rho()<< ", theta = "<< lab.Theta()
       << ", phi = "<< lab.Phi()
       << endl;

  /*

  Double_t masses[3]={0.938,0.135,0.135};

  TGenPhaseSpace event;
  event.SetDecay(W,3,masses);

  event.Generate();
  TLorentzVector *pProton = event.GetDecay(0);
  TLorentzVector *pPi0 = event.GetDecay(1);
  TLorentzVector *pPi02 = event.GetDecay(2);
  
  TH1D *h = new TH1D("his","theta",100,0,180);
  h->Fill(pProton->Theta()*57.3);
Exemple #9
0
void angular::Loop()
{
   if (fChain == 0) return;

   TH1F *Hin_cosThetaStarLead = new TH1F("Hin_cosThetaStarLead","Hin_cosThetaStarLead",100,-1,1);
   TH1F *Hin_cosThetaStarSublead = new TH1F("Hin_cosThetaStarSublead","Hin_cosThetaStarSublead",100,-1,1);
   TH1F *Hin_deltaEta = new TH1F("Hin_deltaEta","Hin_deltaEta",100,-5,5);
   TH1F *Hin_deltaPhi = new TH1F("Hin_deltaPhi","Hin_deltaPhi",50,-1,1);
   
   TH1F *Hout_cosThetaStarLead = new TH1F("Hout_cosThetaStarLead","Hout_cosThetaStarLead",100,-1,1);
   TH1F *Hout_cosThetaStarSublead = new TH1F("Hout_cosThetaStarSublead","Hout_cosThetaStarSublead",100,-1,1);
   TH1F *Hout_deltaEta = new TH1F("Hout_deltaEta","Hout_deltaEta",100,-5,5);
   TH1F *Hout_deltaPhi = new TH1F("Hout_deltaPhi","Hout_deltaPhi",50,-1,1);

   Long64_t nentries = fChain->GetEntriesFast();

   Long64_t nbytes = 0, nb = 0;
   for (Long64_t jentry=0; jentry<nentries;jentry++) {
      Long64_t ientry = LoadTree(jentry);
      if (ientry < 0) break;
      nb = fChain->GetEntry(jentry);   nbytes += nb;

      TLorentzVector myLeadGamma(0,0,0,0);  
      myLeadGamma.SetPtEtaPhiM(leadPt, leadEta, leadPhi, 0.);
      TLorentzVector mySubleadGamma(0,0,0,0);  
      mySubleadGamma.SetPtEtaPhiM(subleadPt, subleadEta, subleadPhi, 0.);

      TLorentzVector grav = myLeadGamma + mySubleadGamma;

      TLorentzVector lead_Gstar(myLeadGamma);
      lead_Gstar.Boost(-grav.BoostVector());
      TLorentzVector sublead_Gstar(mySubleadGamma);
      sublead_Gstar.Boost(-grav.BoostVector());

      float leadCosThStar = lead_Gstar.CosTheta();
      float subleadCosThStar = sublead_Gstar.CosTheta();

      float deltaEta = leadEta-subleadEta;
      float deltaPhi = myLeadGamma.DeltaPhi(mySubleadGamma);
      float cosDPhi = cos(deltaPhi);

      // for data
      if (puweight==0) puweight=1;
      
      if (fabs(mass-755)<20){ 
	Hin_cosThetaStarLead    -> Fill(leadCosThStar,puweight);
	Hin_cosThetaStarSublead -> Fill(subleadCosThStar,puweight);
	Hin_deltaEta->Fill(deltaEta,puweight);
	Hin_deltaPhi->Fill(cosDPhi,puweight);
      } else {
	Hout_cosThetaStarLead    -> Fill(leadCosThStar,puweight);
	Hout_cosThetaStarSublead -> Fill(subleadCosThStar,puweight);
	Hout_deltaEta->Fill(deltaEta,puweight);
	Hout_deltaPhi->Fill(cosDPhi,puweight);
      }
   }

   TFile outfile("outfile.root","RECREATE");
   Hout_cosThetaStarLead->Write();
   Hout_cosThetaStarSublead->Write();
   Hout_deltaEta->Write();
   Hout_deltaPhi->Write();
   Hin_cosThetaStarLead->Write();
   Hin_cosThetaStarSublead->Write();
   Hin_deltaEta->Write();
   Hin_deltaPhi->Write();
}
void pgsAnalysis::Loop()
{

double tHrec, tZ1m, tZ2m, tcosthetaStar, tPhi, tPhi1, tcostheta1, tcostheta2,tHrec_constr,tZ1m_constr, tZ2m_constr;
string ttype;
hists->Branch("Hrec", &tHrec);
hists->Branch("Z1m", &tZ1m);
hists->Branch("Z2m", &tZ2m);
hists->Branch("costhetaStar", &tcosthetaStar);
hists->Branch("Phi", &tPhi);
hists->Branch("Phi1", &tPhi1);
hists->Branch("costheta1", &tcostheta1);
hists->Branch("costheta2", &tcostheta2);
hists->Branch("type", &ttype);

//event type!!
int eeee, xxxx, eexx, xxee;

double Zmass = 91.19;
double vZmass;
if (pairing == 0){
	vZmass = 91.19;
}
else{
	vZmass = 45.;
}
		TVectorT<double> elSum(4);
		TVectorT<double> muSum(4);


	//electrons array
	vector<int> el; int elC = 0;
	//muons array
	vector<int> mu;	int muC = 0;
	//antielectrons array
	vector<int> antiel;	int antielC = 0;
	//antimuons array
	vector<int> antimu;	int antimuC = 0;

	vector<TVector3> leptons;

	TVector3 lep1,lep2,lep3,lep4;
	TVector3 Za, Zb, Zc, Zd, H;


	int lCounter = 0;
	int totaLlCounter = 0;
	int goodEventCounter = 0;
	int histCounter = 0;

	if (fChain == 0) return;
	

	int nentries = n;

// 	cout << " nentries are "<<nentries<<endl;


	Long64_t nbytes = 0, nb = 0;
	for (Long64_t jentry=0; jentry<nentries;jentry++) {
	Long64_t ientry = LoadTree(jentry);
	if (ientry < 0) break;
	nb = fChain->GetEntry(jentry);   nbytes += nb;
	// if (Cut(ientry) < 0) continue;

		el.clear();
		antiel.clear();
		mu.clear();
		antimu.clear();
		lCounter = 0;
		eeee = 0;
		xxxx = 0;
		eexx = 0;
		xxee = 0;

		//particles identified by type, ntrk
		for (int inst = 0; inst < npart; inst++){	// inst from "instance" on the scan tree
			
// 			cout<< " instance "<< inst <<endl;
// 			cout<< pT[inst]<< endl;
	
			//fill el mu vectors
			if ( typ[inst] == 1 && ntrk[inst] == -1){
				el.push_back(inst);
				elC++;
				lCounter++;
				totaLlCounter++;
			}
			if ( typ[inst] == 1 && ntrk[inst] == 1){
				antiel.push_back(inst);
				antielC++;
				lCounter++;
				totaLlCounter++;
			}
			if ( typ[inst] == 2 && ntrk[inst] == -1){
				mu.push_back(inst);
				muC++;
				lCounter++;
				totaLlCounter++;
			}
			if ( typ[inst] == 2 && ntrk[inst] == 1){
				antimu.push_back(inst);
				antimuC++;
				lCounter++;
				totaLlCounter++;
			}
			if ( (typ[inst] == 4 && jmas[inst] > 10. )|| (typ[inst] == 6 && pT[inst] > 10. )){
				lCounter = 0; //dont count the event
			}

		
		}//end instance loop (particles in an event

// 		cout<< "leptons in the event are "<< lCounter<<endl;
// 		if (lCounter == 4) { 

		fillFlag = false;

		// If else if loops reconstructing the particles according to the type 4e,4mu, 2e2mu
		
		if (el.size() == 1 && mu.size() == 1 && antiel.size() == 1 && antimu.size() == 1){ //2e2m
			goodEventCounter++;


			lep1.SetPtEtaPhi( pT[el[0]], eta[el[0]]	, phi[el[0]]);			//set up of lepton four-vectors
			lep2.SetPtEtaPhi( pT[antiel[0]], eta[antiel[0]]	, phi[antiel[0]]);
			lep3.SetPtEtaPhi( pT[mu[0]], eta[mu[0]]	, phi[mu[0]]);
			lep4.SetPtEtaPhi( pT[antimu[0]], eta[antimu[0]]	, phi[antimu[0]]);

			Za = lep1 + lep2;
			Zb = lep3 + lep4;

			mZ1 = sqrt(pow(lep1.Mag()+lep2.Mag(),2)-Za.Mag2());	// reconstruct z masses 
			mZ2 = sqrt(pow(lep3.Mag()+lep4.Mag(),2)-Zb.Mag2());


			//select leading Z
			if(mZ1 > mZ2) { Z1.SetVectM( Za, mZ1); Z2.SetVectM(Zb,mZ2); lep_min1.SetPtEtaPhiE(lep1.Pt(),lep1.Eta(), lep1.Phi(),lep1.Mag()); lep_plus1.SetPtEtaPhiE(lep2.Pt(),lep2.Eta(), lep2.Phi(),lep2.Mag()); lep_min2.SetPtEtaPhiE(lep3.Pt(),lep3.Eta(), lep3.Phi(),lep3.Mag()); lep_plus2.SetPtEtaPhiE(lep4.Pt(),lep4.Eta(), lep4.Phi(),lep4.Mag());eexx++;}	//to set the highest mass the z
			else { Z2.SetVectM( Za, mZ1); Z1.SetVectM(Zb,mZ2); lep_min2.SetPtEtaPhiE(lep1.Pt(),lep1.Eta(), lep1.Phi(),lep1.Mag()); lep_plus2.SetPtEtaPhiE(lep2.Pt(),lep2.Eta(), lep2.Phi(),lep2.Mag()); lep_min1.SetPtEtaPhiE(lep3.Pt(),lep3.Eta(), lep3.Phi(),lep3.Mag()); lep_plus1.SetPtEtaPhiE(lep4.Pt(),lep4.Eta(), lep4.Phi(),lep4.Mag());xxee++;}


			

		fillFlag = true;
		}



		else if (el.size() == 2 && mu.size() == 0  && antiel.size() == 2 && antimu.size() == 0){ //4e
			goodEventCounter++;

			lep1.SetPtEtaPhi( pT[el[0]], eta[el[0]]	, phi[el[0]]);	
			lep2.SetPtEtaPhi( pT[antiel[0]], eta[antiel[0]]	, phi[antiel[0]]);
			lep3.SetPtEtaPhi( pT[el[1]], eta[el[1]]	, phi[el[1]]);	
			lep4.SetPtEtaPhi( pT[antiel[1]], eta[antiel[1]]	, phi[antiel[1]]);

			Za = lep1 + lep2;
			Zb = lep3 + lep4;
			Zc = lep1 + lep4;
			Zd = lep3 + lep2;

			double mZa = sqrt(pow(lep1.Mag()+lep2.Mag(),2)-Za.Mag2());
			double mZb = sqrt(pow(lep3.Mag()+lep4.Mag(),2)-Zb.Mag2());
			double mZc = sqrt(pow(lep1.Mag()+lep4.Mag(),2)-Zc.Mag2());
			double mZd = sqrt(pow(lep2.Mag()+lep3.Mag(),2)-Zd.Mag2());

			double s1a;
			double s1b;
			double s2a;
			double s2b;
			if ( pairing == 0){
			s1a = pow(mZa-vZmass,2) + pow(mZb-Zmass,2);
			s1b = pow(mZa-Zmass,2) + pow(mZb-vZmass,2);
			s2a = pow(mZc-vZmass,2) + pow(mZd-Zmass,2);
			s2b = pow(mZc-Zmass,2) + pow(mZd-vZmass,2);
			}
			else{
			s1a = fabs(mZb-Zmass);
			s1b = fabs(mZa-Zmass);
			s2a = fabs(mZd-Zmass);
			s2b = fabs(mZc-Zmass);
			}

			elSum[0] = s1a;
			elSum[1] = s1b;
			elSum[2] = s2a;
			elSum[3] = s2b;

			int min = TMath::LocMin(4, &elSum[0]);

			if( (min == 0 || min == 1) ){
				if(mZa > mZb) { Z1.SetVectM( Za, mZa); Z2.SetVectM(Zb,mZb); lep_min1.SetPtEtaPhiE(lep1.Pt(),lep1.Eta(), lep1.Phi(),lep1.Mag()); lep_plus1.SetPtEtaPhiE(lep2.Pt(),lep2.Eta(), lep2.Phi(),lep2.Mag()); lep_min2.SetPtEtaPhiE(lep3.Pt(),lep3.Eta(), lep3.Phi(),lep3.Mag()); lep_plus2.SetPtEtaPhiE(lep4.Pt(),lep4.Eta(), lep4.Phi(),lep4.Mag());}	//to set the highest mass the z
				else { Z2.SetVectM( Za, mZa); Z1.SetVectM(Zb,mZb); lep_min2.SetPtEtaPhiE(lep1.Pt(),lep1.Eta(), lep1.Phi(),lep1.Mag()); lep_plus2.SetPtEtaPhiE(lep2.Pt(),lep2.Eta(), lep2.Phi(),lep2.Mag()); lep_min1.SetPtEtaPhiE(lep3.Pt(),lep3.Eta(), lep3.Phi(),lep3.Mag()); lep_plus1.SetPtEtaPhiE(lep4.Pt(),lep4.Eta(), lep4.Phi(),lep4.Mag());}
				
			}
			else if( (min == 2 || min == 3) ){
				if(mZc > mZd) { Z1.SetVectM( Zc, mZc); Z2.SetVectM(Zd,mZd); lep_min1.SetPtEtaPhiE(lep1.Pt(),lep1.Eta(), lep1.Phi(),lep1.Mag()); lep_plus1.SetPtEtaPhiE(lep4.Pt(),lep4.Eta(), lep4.Phi(),lep4.Mag()); lep_min2.SetPtEtaPhiE(lep3.Pt(),lep3.Eta(), lep3.Phi(),lep3.Mag()); lep_plus2.SetPtEtaPhiE(lep2.Pt(),lep2.Eta(), lep2.Phi(),lep2.Mag());}	//to set the highest mass the z
				else { Z2.SetVectM( Zc, mZc); Z1.SetVectM(Zd,mZd); lep_min2.SetPtEtaPhiE(lep1.Pt(),lep1.Eta(), lep1.Phi(),lep1.Mag()); lep_plus2.SetPtEtaPhiE(lep4.Pt(),lep4.Eta(), lep4.Phi(),lep4.Mag()); lep_min1.SetPtEtaPhiE(lep3.Pt(),lep3.Eta(), lep3.Phi(),lep3.Mag()); lep_plus1.SetPtEtaPhiE(lep2.Pt(),lep2.Eta(), lep2.Phi(),lep2.Mag());}


			}
			eeee++;
		fillFlag = true;
		} 


		else if(el.size() == 0 && mu.size() == 2  && antiel.size() == 0 && antimu.size() == 2 )  { //4m
			goodEventCounter++;

			lep1.SetPtEtaPhi( pT[mu[0]], eta[mu[0]]	, phi[mu[0]]);	
			lep2.SetPtEtaPhi( pT[antimu[0]], eta[antimu[0]]	, phi[antimu[0]]);
			lep3.SetPtEtaPhi( pT[mu[1]], eta[mu[1]]	, phi[mu[1]]);	
			lep4.SetPtEtaPhi( pT[antimu[1]], eta[antimu[1]]	, phi[antimu[1]]);

			Za = lep1 + lep2;
			Zb = lep3 + lep4;
			Zc = lep1 + lep4;
			Zd = lep3 + lep2;

			double mZa = sqrt(pow(lep1.Mag()+lep2.Mag(),2)-Za.Mag2());
			double mZb = sqrt(pow(lep3.Mag()+lep4.Mag(),2)-Zb.Mag2());
			double mZc = sqrt(pow(lep1.Mag()+lep4.Mag(),2)-Zc.Mag2());
			double mZd = sqrt(pow(lep2.Mag()+lep3.Mag(),2)-Zd.Mag2());

			double s1a;
			double s1b;
			double s2a;
			double s2b;
			if ( pairing == 0){
			s1a = pow(mZa-vZmass,2) + pow(mZb-Zmass,2);
			s1b = pow(mZa-Zmass,2) + pow(mZb-vZmass,2);
			s2a = pow(mZc-vZmass,2) + pow(mZd-Zmass,2);
			s2b = pow(mZc-Zmass,2) + pow(mZd-vZmass,2);
			}
			else{
			s1a = fabs(mZb-Zmass);
			s1b = fabs(mZa-Zmass);
			s2a = fabs(mZd-Zmass);
			s2b = fabs(mZc-Zmass);
			}


			muSum[0] = s1a;
			muSum[1] = s1b;
			muSum[2] = s2a;
			muSum[3] = s2b;

			int min = TMath::LocMin(4, &muSum[0]);

			if( (min == 0 || min == 1) ){
				if(mZa > mZb) { Z1.SetVectM( Za, mZa); Z2.SetVectM(Zb,mZb); lep_min1.SetPtEtaPhiE(lep1.Pt(),lep1.Eta(), lep1.Phi(),lep1.Mag()); lep_plus1.SetPtEtaPhiE(lep2.Pt(),lep2.Eta(), lep2.Phi(),lep2.Mag()); lep_min2.SetPtEtaPhiE(lep3.Pt(),lep3.Eta(), lep3.Phi(),lep3.Mag()); lep_plus2.SetPtEtaPhiE(lep4.Pt(),lep4.Eta(), lep4.Phi(),lep4.Mag());}	//to set the highest mass the z
				else { Z2.SetVectM( Za, mZa); Z1.SetVectM(Zb,mZb); lep_min2.SetPtEtaPhiE(lep1.Pt(),lep1.Eta(), lep1.Phi(),lep1.Mag()); lep_plus2.SetPtEtaPhiE(lep2.Pt(),lep2.Eta(), lep2.Phi(),lep2.Mag()); lep_min1.SetPtEtaPhiE(lep3.Pt(),lep3.Eta(), lep3.Phi(),lep3.Mag()); lep_plus1.SetPtEtaPhiE(lep4.Pt(),lep4.Eta(), lep4.Phi(),lep4.Mag());}
				
			}
			else if( (min == 2 || min == 3) ){
				if(mZc > mZd) { Z1.SetVectM( Zc, mZc); Z2.SetVectM(Zd,mZd); lep_min1.SetPtEtaPhiE(lep1.Pt(),lep1.Eta(), lep1.Phi(),lep1.Mag()); lep_plus1.SetPtEtaPhiE(lep4.Pt(),lep4.Eta(), lep4.Phi(),lep4.Mag()); lep_min2.SetPtEtaPhiE(lep3.Pt(),lep3.Eta(), lep3.Phi(),lep3.Mag()); lep_plus2.SetPtEtaPhiE(lep2.Pt(),lep2.Eta(), lep2.Phi(),lep2.Mag());}	//to set the highest mass the z
				else { Z2.SetVectM( Zc, mZc); Z1.SetVectM(Zd,mZd); lep_min2.SetPtEtaPhiE(lep1.Pt(),lep1.Eta(), lep1.Phi(),lep1.Mag()); lep_plus2.SetPtEtaPhiE(lep4.Pt(),lep4.Eta(), lep4.Phi(),lep4.Mag()); lep_min1.SetPtEtaPhiE(lep3.Pt(),lep3.Eta(), lep3.Phi(),lep3.Mag()); lep_plus1.SetPtEtaPhiE(lep2.Pt(),lep2.Eta(), lep2.Phi(),lep2.Mag());}


			}
		xxxx++;
		fillFlag = true;
		}


		if ( fillFlag == true && goodEventCounter < 25001) {	//if it fullfills the specs then fill and find angles

			rec_H = Z1 + Z2;
			double Hmass = rec_H.M();
			tHrec = Hmass;
// 			cout<<tHrec<<endl;

			double Z1mass = Z1.M();
			tZ1m = Z1mass;
			double Z2mass = Z2.M();
			tZ2m = Z2mass;
			double ptlepp1 = lep_plus1.Pt();
			double ptlepm1 = lep_min1.Pt();
			double ptlepp2 = lep_plus2.Pt();
			double ptlepm2 = lep_min2.Pt();
			double dR1 = sqrt(pow(fabs(lep_min1.Eta() - lep_plus1.Eta()),2)+pow(fabs(lep_min1.DeltaPhi(lep_plus1)),2));
			double dR2 = sqrt(pow(fabs(lep_min2.Eta() - lep_plus2.Eta()),2)+pow(fabs(lep_min2.DeltaPhi(lep_plus2)),2));

// 			if ( /*Hmass<120 || Hmass>130 || */Z1mass < 49 || Z1mass>107 || Z2mass < 12 || Z2mass> 115 ){continue;}	//constrains		
	
			//filling the simple histogram values
			h_Z1_m -> Fill(Z1.M());
			h_Z1_E -> Fill(Z1.E());
			h_Z1_Pt -> Fill(Z1.Pt());
			h_Z1_eta -> Fill(Z1.Eta());
			h_Z1_phi -> Fill(Z1.Phi());
	
			h_Z2_m -> Fill(Z2.M());
			h_Z2_E -> Fill(Z2.E());
			h_Z2_Pt -> Fill(Z2.Pt());
			h_Z2_eta -> Fill(Z2.Eta());
			h_Z2_phi -> Fill(Z2.Phi());
	
	
			h_rec_H_m	-> Fill(Hmass);
			h_rec_H_E	-> Fill(rec_H.E());
			h_rec_H_Pt	-> Fill(rec_H.Pt());
			h_rec_H_eta	-> Fill(rec_H.Eta());
			h_rec_H_phi	-> Fill(rec_H.Phi());	

			h_lep_plus1_E	-> Fill(lep_plus1.E());
			h_lep_plus1_Pt	-> Fill(ptlepp1);
			h_lep_plus1_eta	-> Fill(lep_plus1.Eta());
			h_lep_plus1_phi	-> Fill(lep_plus1.Phi());

			h_lep_min1_E	-> Fill(lep_min1.E());
			h_lep_min1_Pt	-> Fill(ptlepm1);
			h_lep_min1_eta	-> Fill(lep_min1.Eta());
			h_lep_min1_phi	-> Fill(lep_min1.Phi());

			h_lep_plus2_E	-> Fill(lep_plus2.E());
			h_lep_plus2_Pt	-> Fill(ptlepp2);
			h_lep_plus2_eta	-> Fill(lep_plus2.Eta());
			h_lep_plus2_phi	-> Fill(lep_plus2.Phi());

			h_lep_min2_E	-> Fill(lep_min2.E());
			h_lep_min2_Pt	-> Fill(ptlepm2);
			h_lep_min2_eta	-> Fill(lep_min2.Eta());
			h_lep_min2_phi	-> Fill(lep_min2.Phi());	

		//reconstructing the two lepton pairs Lorentz vectors
		lpair1 = lep_plus1 + lep_min1;
		lpair2 = lep_plus2 + lep_min2;

		//constructing 3-vectors in the lab frame
		lep_plus1_lab 	= lep_plus1.Vect();
		lep_plus2_lab 	= lep_plus2.Vect();	//.Vect() gives 3 vector from 4vector
		lep_min1_lab 	= lep_min1.Vect();	
		lep_min2_lab 	= lep_min2.Vect();
		lpair1_lab 	= lep_plus1_lab.Cross(lep_min1_lab);	
		lpair2_lab 	= lep_plus2_lab.Cross(lep_min2_lab);

// 		cout << " pt of lepton pair1 on rest frame is: "<< lpair1.Perp()<<endl;


	   	//Filling up Histograms with angles defined in the lab frame
		h_angle_lab_pair1 -> Fill(lep_plus1_lab.Angle(lep_min1_lab));
		h_angle_lab_pair2 -> Fill(lep_plus2_lab.Angle(lep_min2_lab));


       		//Filling up histograms with variables from articles
       		h_angle_lab_deleta1	-> Fill(fabs(lep_min1.Eta() - lep_plus1.Eta()));
       		h_angle_lab_delphi1	-> Fill(fabs(lep_min1.DeltaPhi(lep_plus1)));
       		h_angle_lab_deleta2	-> Fill(fabs(lep_min2.Eta() - lep_plus2.Eta()));
       		h_angle_lab_delphi2	-> Fill(fabs(lep_min2.DeltaPhi(lep_plus2)));


	   	//Looking at the Higgs rest frame
	   	TVector3 boost_rH 	= -rec_H.BoostVector(); //NOTE the minus sign! WHY - sign???
	   	TVector3 boost_rZ1	= -Z1.BoostVector();
	   	TVector3 boost_rZ2	= -Z2.BoostVector();	
	   	Higgs_rest	= rec_H;
	   	Z1_rH		= Z1;
	   	Z2_rH		= Z2;
	   	lep_p1_rH	= lep_plus1;	//
	   	lep_m1_rH	= lep_min1;
	   	lep_p2_rH	= lep_plus2;
	   	lep_m2_rH	= lep_min2;
	   	lep_p1_rZ1	= lep_plus1;
	   	lep_m2_rZ2	= lep_min2;
	   	lep_p2_rZ2	= lep_plus2;
	   	lep_m1_rZ1	= lep_min1;

	   	//Boosting vectors to the Higgs rest frame
	   	Higgs_rest.Boost(boost_rH);
	   	Z1_rH.Boost(boost_rH);
	   	Z2_rH.Boost(boost_rH);
	   	lep_p1_rH.Boost(boost_rH);
	   	lep_m1_rH.Boost(boost_rH);
	   	lep_p2_rH.Boost(boost_rH);
	   	lep_m2_rH.Boost(boost_rH);

	   	//Boosting leptons to Z rest frames
	   	lep_p1_rZ1.Boost(boost_rZ1);
	   	lep_m1_rZ1.Boost(boost_rZ1);
	   	lep_p2_rZ2.Boost(boost_rZ2);
	   	lep_m2_rZ2.Boost(boost_rZ2);

	   	//Setting 3Vectors in Higgs rest frame
	   	Z3_1_rH		= Z1_rH.Vect();
	   	Z3_2_rH		= Z2_rH.Vect();
	   	lep3_plus1_rH 	= lep_p1_rH.Vect();
	   	lep3_min1_rH	= lep_m1_rH.Vect();
	   	lep3_plus2_rH 	= lep_p2_rH.Vect();
	   	lep3_min2_rH	= lep_m2_rH.Vect();
		TVector3 Z3_1plane_rH 	= lep3_plus1_rH.Cross(lep3_min1_rH);	//wrong?
	   	TVector3 Z3_2plane_rH 	= lep3_plus2_rH.Cross(lep3_min2_rH);

	   	//Setting 3Vectors in Z1/Z2 rest frame
	   	lep3_plus1_rZ1	= lep_p1_rZ1.Vect();
	   	lep3_plus2_rZ2	= lep_p2_rZ2.Vect();
	   	lep3_min1_rZ1	= lep_m1_rZ1.Vect();
	   	lep3_min2_rZ2	= lep_m2_rZ2.Vect();

	   	//Filling up histogram for the phi angle distribution

		//pairnoume ta monadiaia dianysmata twn kathetwn pediwn, prwta ypologizoume to metro tous, meta eswteriko ginomeno, meta tokso tou costheta tous
		double metro1 = sqrt((pow(Z3_1plane_rH.X(),2))+(pow(Z3_1plane_rH.Y(),2))+(pow(Z3_1plane_rH.Z(),2)));
		double metro2 = sqrt((pow(Z3_2plane_rH.X(),2))+(pow(Z3_2plane_rH.Y(),2))+(pow(Z3_2plane_rH.Z(),2)));
		TVector3 Z3_1plane_rH_un = Z3_1plane_rH.Unit();
		TVector3 Z3_2plane_rH_un = Z3_2plane_rH.Unit();

		TVector3 drtPlane = Z3_1plane_rH_un.Cross(Z3_2plane_rH_un);
		double phi = acos(-Z3_1plane_rH_un.Dot(Z3_2plane_rH_un))*(Z3_1_rH.Dot(skata))/fabs(Z3_1_rH.Dot(skata));

		h_angle_rH_phi	-> Fill( phi );
		tPhi = phi;		



		//****Phi one angle , same procedure as before. Now the plane is the first Z boson vector with beam axis, so they form a plane, phi1 is angle between this plane and the Z1 plane (apo to decay twn 2 leptoniwn)
		TVector3 niScatter_un = (beamAxis.Cross(Z3_1_rH)).Unit();
		TVector3 drtPlane2 = Z3_1plane_rH_un.Cross(niScatter_un);
		double phiOne = acos(Z3_1plane_rH_un.Dot(niScatter_un))*(Z3_1_rH.Dot(skata2))/fabs(Z3_1_rH.Dot(skata2));
		h_angle_rH_phiOne	-> Fill( phiOne );
		tPhi1 = phiOne;


	   	//Filling up histogram for theta* angle: Z1/Z2 with Higgs boost vector
	   	h_angle_rH_thetaZ2	-> Fill(Z3_2_rH.CosTheta());
		
		double cosThetaStar = Z3_1_rH.CosTheta();
		h_angle_rH_thetaZ1	-> Fill(cosThetaStar);
		tcosthetaStar = cosThetaStar;

		//  boosting the z to the other z frame
		TLorentzVector Z_1_rZ2 = Z1;
		Z_1_rZ2.Boost(boost_rZ2);
		TVector3 Z3_1_rZ2 = Z_1_rZ2.Vect();
		TLorentzVector Z_2_rZ1 = Z2;
		Z_2_rZ1.Boost(boost_rZ1);
		TVector3 Z3_2_rZ1 = Z_2_rZ1.Vect();
		double cosTheta1 = cos(lep3_min1_rZ1.Angle(-Z3_2_rZ1));
		double cosTheta2 = cos(lep3_min2_rZ2.Angle(-Z3_1_rZ2));
	   	h_angle_rZ1_lp1Z1	-> Fill(cos(lep3_plus1_rZ1.Angle(-Z3_2_rZ1)));	
	   	h_angle_rZ1_lm1Z1	-> Fill(cosTheta1);	// theta1
	   	h_angle_rZ2_lp2Z2	-> Fill(cos(lep3_plus2_rZ2.Angle(-Z3_1_rZ2)));	
	   	h_angle_rZ2_lm2Z2	-> Fill(cosTheta2);	// theta2
		tcostheta1 = cosTheta1;
		tcostheta2 = cosTheta2;	

       		h_angle_rH_delphi1	-> Fill(fabs(lep_p1_rH.DeltaPhi(lep_m1_rH)));
		h_angle_rH_delphi2	-> Fill(fabs(lep_p2_rH.DeltaPhi(lep_m2_rH)));

		h_mZ1mZ2		-> Fill(Z1.M(),Z2.M());
		h_mVsPtZ1		-> Fill(Z1.M(),Z1.Pt());

		h_delphi1VsPtZ1_lab	-> Fill(Z1.Pt(),fabs(lep_min1.DeltaPhi(lep_plus1)));
		h_delphi2VsPtZ2_lab	-> Fill(Z2.Pt(),fabs(lep_min2.DeltaPhi(lep_plus2)));

		if (eexx ==1){ttype = "eexx";}
		else if(xxee ==1){ttype = "xxee";}
		else if(eeee ==1){ttype = "eeee";}
		else if(xxxx ==1){ttype = "xxxx";}
		hists->Fill();
		histCounter++;
		
		hists->Close();
		}	//end if fill

		////////////// fill out the decay type

		
		
	// filling the TTree


	}//end entries loop (events)

	//some regular reports
	cout<<endl;
	cout<<" good events are "<<goodEventCounter<<endl;
	cout<<" we see % "<< (double) goodEventCounter/n <<endl;

	cout<<endl;
	cout<<" histogram fills are "<<histCounter<<endl;
// 	cout<<" we see % "<< (double) goodEventCounter/n <<endl;




}//end loop void
Exemple #11
0
void PlotTheta( TString inputfilename, TString outputfilename = "output.root"){
//    infile= new TFile("../PATGrid.SM.10k.root","READ");
    infile = new TFile(inputfilename, "READ");
    tree = (TTree*)infile->Get("Event");
    outputFile = new TFile(outputfilename, "RECREATE");
    outTree = new TTree("MyTree","Untersuchung der RekoObjekte");

    //TH2::SetDefaultSumw2();

    histogram__CosThetaDiff = new TH1D("histogram__CosThetaDiff", "Differenz CosTheta gen-reko", 400, -2, 2);
    histogram__CosTheta_GenReko = new TH2D("histogram__CosTheta_GenReko", "Reko-cos(theta) gegen Gen-cos(theta)", 50, -1, 1, 50, -1, 1);

    histogram__gen_A = new TH2D("histogram__gen_A", "histogram__gen_A", 5, -1, 1, 5, -1, 1);
    histogram__gen_N = new TH2D("histogram__gen_N", "histogram__gen_N", 5, -1, 1, 5, -1, 1);

    histogram__gen_LL = new TH2D("histogram__gen_LL", "histogram__gen_LL", 5, -1, 1, 5, -1, 1);
    histogram__gen_LR = new TH2D("histogram__gen_LR", "histogram__gen_LR", 5, -1, 1, 5, -1, 1);
    histogram__gen_RR = new TH2D("histogram__gen_RR", "histogram__gen_RR", 5, -1, 1, 5, -1, 1);
    histogram__gen_RL = new TH2D("histogram__gen_RL", "histogram__gen_RL", 5, -1, 1, 5, -1, 1);

    histogram__gen_Correlation = new TH2D("histogram__gen_Correlation", "histogram__gen_Correlation", 5, -1, 1, 5, -1, 1);

    histogram__A = new TH2D("histogram__A", "histogram__A", 5, -1, 1, 5, -1, 1);
    histogram__N = new TH2D("histogram__N", "histogram__N", 5, -1, 1, 5, -1, 1);

    histogram__Correlation = new TH2D("histogram__Correlation", "histogram__Correlation", 5, -1, 1, 5, -1, 1);
    histogram__Correlation_L15_B50_T1 = new TH2D("histogram__Correlation_L15_B50_T1", "histogram__Correlation_L15_B50_T1", 5, -1, 1, 5, -1, 1);
    histogram__A_L15_B50_T1 = new TH2D("histogram__A_L15_B50_T1", "histogram__A_L15_B50_T1", 5, -1, 1, 5, -1, 1);
    histogram__N_L15_B50_T1 = new TH2D("histogram__N_L15_B50_T1", "histogram__N_L15_B50_T1", 5, -1, 1, 5, -1, 1);
    histogram__Correlation_L20 = new TH2D("histogram__Correlation_L20", "histogram__Correlation_L20", 5, -1, 1, 5, -1, 1);
    histogram__A_L20 = new TH2D("histogram__A_L20", "histogram__A_L20", 5, -1, 1, 5, -1, 1);
    histogram__N_L20 = new TH2D("histogram__N_L20", "histogram__N_L20", 5, -1, 1, 5, -1, 1);
    histogram__Correlation_L20_B40 = new TH2D("histogram__Correlation_L20_B40", "histogram__Correlation_L20_B40", 5, -1, 1, 5, -1, 1);
    histogram__A_L20_B40 = new TH2D("histogram__A_L20_B40", "histogram__A_L20_B40", 5, -1, 1, 5, -1, 1);
    histogram__N_L20_B40 = new TH2D("histogram__N_L20_B40", "histogram__N_L20_B40", 5, -1, 1, 5, -1, 1);
    
    histogram__Correlation_L20_B30_T1 = new TH2D("histogram__Correlation_L20_B30_T1", "histogram__Correlation_L20_B30_T1", 5, -1, 1, 5, -1, 1);
    histogram__A_L20_B30_T1 = new TH2D("histogram__A_L20_B30_T1", "histogram__A_L20_B30_T1", 5, -1, 1, 5, -1, 1);
    histogram__N_L20_B30_T1 = new TH2D("histogram__N_L20_B30_T1", "histogram__N_L20_B30_T1", 5, -1, 1, 5, -1, 1);

    histogram__Correlation_L20_B40_T1 = new TH2D("histogram__Correlation_L20_B40_T1", "histogram__Correlation_L20_B40_T1", 5, -1, 1, 5, -1, 1);
    histogram__A_L20_B40_T1 = new TH2D("histogram__A_L20_B40_T1", "histogram__A_L20_B40_T1", 5, -1, 1, 5, -1, 1);
    histogram__N_L20_B40_T1 = new TH2D("histogram__N_L20_B40_T1", "histogram__N_L20_B40_T1", 5, -1, 1, 5, -1, 1);
    histogram__Correlation_T1 = new TH2D("histogram__Correlation_T1", "histogram__Correlation_T1", 5, -1, 1, 5, -1, 1);
    histogram__A_T1 = new TH2D("histogram__A_T1", "histogram__A_T1", 5, -1, 1, 5, -1, 1);
    histogram__N_T1 = new TH2D("histogram__N_T1", "histogram__N_T1", 5, -1, 1, 5, -1, 1);



    histogram__CosThetaDiff_TTbarPt = new TH2D("histogram__CosThetaDiff_TTbarPt", "histogram__CosThetaDiff_TTbarPt", 100, 0, 1000, 400, -2, 2);


    histogram__LeptonRelIso = new TH1D("histogram__LeptonRelIso", "histogram__LeptonRelIso", 101, 0, 1.01);


    histogram__semilepton_BLeptonMinus = new TH1D("histogram__semilepton_BLeptonMinus","histogram__semilepton_BLeptonMinus", 200, -1, 1);
    histogram__semilepton_BLeptonPlus = new TH1D("histogram__semilepton_BLeptonPlus","histogram__semilepton_BLeptonPlus", 200, -1, 1);



    histogram_nupx_gen_reco = new TH2D(" histogram_nupx_gen_reco", " histogram_nupx_gen_reco", 600, -300, 300, 600, -300, 300);
    histogram_nupy_gen_reco = new TH2D(" histogram_nupy_gen_reco", " histogram_nupy_gen_reco", 600, -300, 300, 600, -300, 300);
    histogram_nupz_gen_reco = new TH2D(" histogram_nupz_gen_reco", " histogram_nupz_gen_reco", 600, -300, 300, 600, -300, 300);

    histogram_nubpx_gen_reco = new TH2D(" histogram_nubpx_gen_reco", " histogram_nubpx_gen_reco", 600, -300, 300, 600, -300, 300);
    histogram_nubpy_gen_reco = new TH2D(" histogram_nubpy_gen_reco", " histogram_nubpy_gen_reco", 600, -300, 300, 600, -300, 300);
    histogram_nubpz_gen_reco = new TH2D(" histogram_nubpz_gen_reco", " histogram_nubpz_gen_reco", 600, -300, 300, 600, -300, 300);

    outTree->Branch("EventIsGood", &EventIsGood, "Event ist rekonstruiert/I");
    outTree->Branch("numberOfJets", &numberOfJets, "Anzahl der Jets/I");
    outTree->Branch("numberOfGoodJets", &numberOfGoodJets, "Anzahl der guten Jets/I");

    outTree->Branch("CosThetaDiff" ,&CosThetaDiff ,"Differenz im cosTheta Reko zu Gen/D");
    outTree->Branch("CosThetaPlus" ,&CosThetaPlus ,"cosTheta LeptonPlus/D");
    outTree->Branch("CosThetaMinus" ,&CosThetaMinus ,"cosTheta LeptonMinus/D");
    outTree->Branch("RekoCosThetaPlus" ,&RekoCosThetaPlus ,"cosTheta RekoLeptonPlus/D");
    outTree->Branch("RekoCosThetaMinus" ,&RekoCosThetaMinus ,"cosTheta RekoLeptonMinus/D");

    outTree->Branch("CosLeptonAngleD", &CosLeptonAngleD, "CosinusLeptonWinkel D/D");
    outTree->Branch("CosRekoLeptonAngleD", &CosRekoLeptonAngleD, "CosinusRekoLeptonWinkel D/D");

    outTree->Branch("TTbar_Pt", &TTbar_Pt, "Pt des TTbarsystems Generator/D");
    outTree->Branch("RekoTTbar_Pt", &RekoTTbar_Pt, "Pt des TTbarsystems Reko/D");
    outTree->Branch("TTbar_M", &TTbar_M, "Masse des TTbarsystems Generator/D");
    outTree->Branch("RekoTTbar_M", &RekoTTbar_M, "Masse des TTbarsystems Reko/D");
    outTree->Branch("Top_Pt", &Top_Pt, "Pt des Tops Generator/D");
    outTree->Branch("Top_M", &Top_M, "M des Tops Generator/D");
    outTree->Branch("AntiTop_Pt", &AntiTop_Pt, "Pt des AntiTops Generator/D");
    outTree->Branch("AntiTop_M", &AntiTop_M, "M des AntiTops Generator/D");
    outTree->Branch("RekoTop_Pt", &RekoTop_Pt, "Pt des Tops Reko/D");
    outTree->Branch("RekoAntiTop_Pt", &RekoAntiTop_Pt, "Pt des AntiTops Reko/D");
    outTree->Branch("RekoTop_M", &RekoTop_M, "M des Tops Reko/D");
    outTree->Branch("RekoAntiTop_M", &RekoAntiTop_M, "M des AntiTops Reko/D");
    outTree->Branch("Nu_Px", &Nu_Px, "Px des Neutrinos Generator/D");
    outTree->Branch("Nu_Py", &Nu_Py, "Py des Neutrinos Generator/D");
    outTree->Branch("Nu_Pz", &Nu_Pz, "Pz des Neutrinos Generator/D");
    outTree->Branch("AntiNu_Px", &AntiNu_Px, "Px des AntiNeutrinos Generator/D");
    outTree->Branch("AntiNu_Py", &AntiNu_Py, "Py des AntiNeutrinos Generator/D");
    outTree->Branch("AntiNu_Pz", &AntiNu_Pz, "Pz des AntiNeutrinos Generator/D");
    outTree->Branch("RekoNu_Px", &RekoNu_Px, "Px des Neutrinos Reko/D");
    outTree->Branch("RekoNu_Py", &RekoNu_Py, "Py des Neutrinos Reko/D");
    outTree->Branch("RekoNu_Pz", &RekoNu_Pz, "Pz des Neutrinos Reko/D");
    outTree->Branch("RekoAntiNu_Px", &RekoAntiNu_Px, "Px des AntiNeutrinos Reko/D");
    outTree->Branch("RekoAntiNu_Py", &RekoAntiNu_Py, "Py des AntiNeutrinos Reko/D");
    outTree->Branch("RekoAntiNu_Pz", &RekoAntiNu_Pz, "Pz des AntiNeutrinos Reko/D");

    outTree->Branch("BestNu_Px", &BestNu_Px, "Px des Neutrinos Best/D");
    outTree->Branch("BestNu_Py", &BestNu_Py, "Py des Neutrinos Best/D");
    outTree->Branch("BestNu_Pz", &BestNu_Pz, "Pz des Neutrinos Best/D");
    outTree->Branch("BestAntiNu_Px", &BestAntiNu_Px, "Px des AntiNeutrinos Best/D");
    outTree->Branch("BestAntiNu_Py", &BestAntiNu_Py, "Py des AntiNeutrinos Best/D");
    outTree->Branch("BestAntiNu_Pz", &BestAntiNu_Pz, "Pz des AntiNeutrinos Best/D");

    outTree->Branch("Lepton_Pt", &Lepton_Pt, "kleineres Pt der beiden gewaehlten Leptonen/D");
    outTree->Branch("BJet_Et", &BJet_Et,"niedrigieres Et der BJets/D");
    outTree->Branch("BJet_Tag_TrkCount", &BJet_Tag_TrkCount,"niedrigierer BTag der BJets/D");
    outTree->Branch("BJet_Tag_SVsimple", &BJet_Tag_SVsimple,"niedrigierer BTag der BJets/D");
    outTree->Branch("BJet_Tag_SVcomb", &BJet_Tag_SVcomb,"niedrigierer BTag der BJets/D");
    outTree->Branch("BJet_Disc", &BJet_Disc,"niedrigierer Discriminator der BJets/D");
    outTree->Branch("Lepton1_Id", &Lepton1_Id, "PdgId des ersten Leptons/I");
    outTree->Branch("Lepton2_Id", &Lepton2_Id, "PdgId des zweiten Leptons/I");
    outTree->Branch("Lepton_Mass", &Lepton_Mass, "inv. Masse der beiden Leptonen/D");

    outTree->Branch("BJet_Angle", &BJet_Angle, "Winkel bJet zu Quark/D");
    outTree->Branch("BbarJet_Angle", &BbarJet_Angle, "Winkel bbarJet zu Quark/D");
    outTree->Branch("LeptonPlus_Angle", &LeptonPlus_Angle, "Winkel LeptonPlus zu Lepton Gen /D");
    outTree->Branch("LeptonMinus_Angle", &LeptonMinus_Angle, "Winkel LeptonMinus zu Lepton Gen /D");
    outTree->Branch("RekoNu_Angle", &RekoNu_Angle, "Winkel RekoNu zu GenNu/D");
    outTree->Branch("RekoAntiNu_Angle", &RekoAntiNu_Angle, "Winkel RekoAntiNu zu GenAntiNu/D");
    outTree->Branch("BestNu_Angle", &BestNu_Angle, "Winkel BestNu zu GenNu/D");
    outTree->Branch("BestAntiNu_Angle", &BestAntiNu_Angle, "Winkel BestAntiNu zu GenAntiNu/D");


    histogram__gen_Correlation->Sumw2();
    histogram__Correlation->Sumw2();
    histogram__gen_A->Sumw2();
    histogram__A->Sumw2();
    histogram__gen_N->Sumw2();
    histogram__N->Sumw2();


    double PatJetsPx[50];
    double PatJetsPy[50];
    double PatJetsPz[50];
    double PatJetsE[50];
    double PatJetsEt[50];

    double PatLeptonsPx[20];
    double PatLeptonsPy[20];
    double PatLeptonsPz[20];
    double PatLeptonsPt[20];
    double PatLeptonsE[20];
    int PatLeptonsCharge[20];
    int PatLeptonsPdgId[20];
    double PatLeptonsTrkIso[20];
    double PatLeptonsCaloIso[20];

    double PatJetsBTag_TrkCount[50];
    double PatJetsBTag_SVsimple[50];
    double PatJetsBTag_SVcomb[50];
    double PatJetsCharge[50];
    double PatJetsBQuarkDeltaR[50];
    double PatJetsBbarQuarkDeltaR[50];
    
    int numberOfPatMuons;
    int numberOfPatElectrons;
    int numberOfPatLeptons;
    int numberOfPatJets;

    int numberOfLeptons;



    TLorentzVector *pTop;           //FROM TREE
    TLorentzVector *pAntiTop;       //FROM TREE
    TLorentzVector *pLeptonPlus;    //FROM TREE
    TLorentzVector *pLeptonMinus;   //FROM TREE
    TLorentzVector *pBQuark;        //FROM TREE
    TLorentzVector *pBbarQuark;     //FROM TREE
    TLorentzVector* pGenNu;         //FROM TREE
    TLorentzVector* pGenAntiNu;     //FROM TREE

    TLorentzVector *pTTbar;
    TLorentzVector *pTopBoosted;
    TLorentzVector *pAntiTopBoosted;
    TLorentzVector *pLeptonPlusBoosted;
    TLorentzVector *pLeptonMinusBoosted;

    TLorentzVector *pJet[50];

    TLorentzVector *pBJet1;
    TLorentzVector *pBJet2;
    TLorentzVector *pRekoNu1;
    TLorentzVector *pRekoAntiNu1;
    TLorentzVector *pRekoNu2;
    TLorentzVector *pRekoAntiNu2;

    TLorentzVector *pRekoLeptonPlus;
    TLorentzVector *pRekoLeptonMinus;
    TLorentzVector *pBJet;
    TLorentzVector *pBbarJet;
    TLorentzVector *pRekoNu;
    TLorentzVector *pRekoAntiNu;

    TLorentzVector *pBestNu;
    TLorentzVector *pBestAntiNu;
    TLorentzVector *pBestNu2;
    TLorentzVector *pBestAntiNu2;

    TLorentzVector *pRekoTop;
    TLorentzVector *pRekoAntiTop;

    TLorentzVector *pRekoTTbar;
    TLorentzVector *pRekoTopBoosted;
    TLorentzVector *pRekoAntiTopBoosted;
    TLorentzVector *pRekoLeptonPlusBoosted;
    TLorentzVector *pRekoLeptonMinusBoosted;

    TLorentzVector *pNu;
    TLorentzVector *pAntiNu;

    TLorentzVector *pBBoosted;
    TLorentzVector *pBbarBoosted;

    pTop = new TLorentzVector(0,0,0,0);
    pAntiTop = new TLorentzVector(0,0,0,0);
    pLeptonPlus = new TLorentzVector(0,0,0,0);
    pLeptonMinus = new TLorentzVector(0,0,0,0);
    pBQuark = new TLorentzVector(0,0,0,0);
    pBbarQuark = new TLorentzVector(0,0,0,0);
    pGenNu = new TLorentzVector(0,0,0,0);
    pGenAntiNu = new TLorentzVector(0,0,0,0);

    pTTbar = new TLorentzVector(0,0,0,0);
    pTopBoosted = new TLorentzVector(0,0,0,0);
    pAntiTopBoosted = new TLorentzVector(0,0,0,0);
    pLeptonPlusBoosted = new TLorentzVector(0,0,0,0);
    pLeptonMinusBoosted = new TLorentzVector(0,0,0,0);

    pRekoTop = new TLorentzVector(0,0,0,0);
    pRekoAntiTop = new TLorentzVector(0,0,0,0);
    pRekoLeptonPlus = new TLorentzVector(0,0,0,0);
    pRekoLeptonMinus = new TLorentzVector(0,0,0,0);
    pRekoNu = new TLorentzVector(0,0,0,0);
    pRekoAntiNu = new TLorentzVector(0,0,0,0);

    pBestNu = new TLorentzVector(0,0,0,0);
    pBestAntiNu = new TLorentzVector(0,0,0,0);
    pBestNu2 = new TLorentzVector(0,0,0,0);
    pBestAntiNu2 = new TLorentzVector(0,0,0,0);

    pRekoTTbar = new TLorentzVector(0,0,0,0);
    pRekoTopBoosted = new TLorentzVector(0,0,0,0);
    pRekoAntiTopBoosted = new TLorentzVector(0,0,0,0);
    pRekoLeptonPlusBoosted = new TLorentzVector(0,0,0,0);
    pRekoLeptonMinusBoosted = new TLorentzVector(0,0,0,0);    

    pNu = new TLorentzVector(0,0,0,0);
    pAntiNu = new TLorentzVector(0,0,0,0);
    pBJet1 = new TLorentzVector(0,0,0,0);
    pBJet2 = new TLorentzVector(0,0,0,0);
    pRekoNu1 = new TLorentzVector(0,0,0,0);
    pRekoAntiNu1 = new TLorentzVector(0,0,0,0);
    pRekoNu2 = new TLorentzVector(0,0,0,0);
    pRekoAntiNu2 = new TLorentzVector(0,0,0,0);
    pBJet = new TLorentzVector(0,0,0,0);
    pBbarJet = new TLorentzVector(0,0,0,0);

    pBBoosted = new TLorentzVector(0,0,0,0);
    pBbarBoosted = new TLorentzVector(0,0,0,0);

    for(int i=0; i<50;i++) pJet[i] = new TLorentzVector(0,0,0,0);

    double mass_a = 170.0;
    double mass_b = 175.0;
    calc Poly(mass_a, mass_b, outputFile);
    

    tree->SetBranchAddress("pTop",                &pTop);
    tree->SetBranchAddress("pAntiTop",            &pAntiTop);
    tree->SetBranchAddress("pLeptonPlus",         &pLeptonPlus);
    tree->SetBranchAddress("pLeptonMinus",        &pLeptonMinus);
    tree->SetBranchAddress("pBQuark",             &pBQuark);
    tree->SetBranchAddress("pBbarQuark",          &pBbarQuark);

    tree->SetBranchAddress("PatLeptonsPx",           PatLeptonsPx);
    tree->SetBranchAddress("PatLeptonsPy",           PatLeptonsPy);
    tree->SetBranchAddress("PatLeptonsPz",           PatLeptonsPz);
    tree->SetBranchAddress("PatLeptonsPt",           PatLeptonsPt);
    tree->SetBranchAddress("PatLeptonsE",            PatLeptonsE);
    tree->SetBranchAddress("PatLeptonsCharge",       PatLeptonsCharge);
    tree->SetBranchAddress("PatLeptonsPdgId",        PatLeptonsPdgId);
    tree->SetBranchAddress("PatLeptonsTrkIso",       PatLeptonsTrkIso);
    tree->SetBranchAddress("PatLeptonsCaloIso",      PatLeptonsCaloIso);

    tree->SetBranchAddress("PatJetsPx",           PatJetsPx);
    tree->SetBranchAddress("PatJetsPy",           PatJetsPy);
    tree->SetBranchAddress("PatJetsPz",           PatJetsPz);
    tree->SetBranchAddress("PatJetsE",            PatJetsE);
    tree->SetBranchAddress("PatJetsEt",           PatJetsEt);
    
    tree->SetBranchAddress("PatJetsCharge", 	        PatJetsCharge);
    tree->SetBranchAddress("PatJetsBTag_TrkCount",	 	PatJetsBTag_TrkCount);
    tree->SetBranchAddress("PatJetsBTag_SVsimple",	 	PatJetsBTag_SVsimple);
    tree->SetBranchAddress("PatJetsBTag_SVcomb",	 	PatJetsBTag_SVcomb);
    tree->SetBranchAddress("PatJetsBQuarkDeltaR",     PatJetsBQuarkDeltaR);
    tree->SetBranchAddress("PatJetsBbarQuarkDeltaR",  PatJetsBbarQuarkDeltaR);
   
    tree->SetBranchAddress("numberOfPatMuons",	        &numberOfPatMuons);
    tree->SetBranchAddress("numberOfPatElectrons",	&numberOfPatElectrons);
    tree->SetBranchAddress("numberOfPatLeptons",	&numberOfPatLeptons);
    tree->SetBranchAddress("numberOfPatJets",	        &numberOfPatJets);

    tree->SetBranchAddress("numberOfLeptons",	&numberOfLeptons);

    tree->SetBranchAddress("pGenNu",          &pGenNu);
    tree->SetBranchAddress("pGenAntiNu",      &pGenAntiNu);
 
    int nEvents = (int)tree->GetEntries();
    //nEvents = 5000;
    int EventCounter = 0;
    cout << "Anzahl Ereignisse: " << nEvents << endl;
    for(int iEvent=1; iEvent<nEvents;iEvent++){

        tree->GetEntry(iEvent);

        EventCounter++;

  
        if(iEvent%10000 == 1)
        {
            cout << "Event " << iEvent << endl;
        }
        
        EventIsGood = 0;
        
// GENERATOR THETA

        w_A = 0;
        w_N = 0;
        
        *pTTbar=(*pTop+*pAntiTop);
        *pTopBoosted = *pTop;
        *pAntiTopBoosted = *pAntiTop;
        *pLeptonPlusBoosted = *pLeptonPlus;
        *pLeptonMinusBoosted = *pLeptonMinus;
        *pBBoosted = *pBQuark;
        *pBbarBoosted = *pBbarQuark;

        pAntiTopBoosted->Boost(-pTTbar->BoostVector());
        pTopBoosted->Boost(-pTTbar->BoostVector());
        pLeptonPlusBoosted->Boost(-pTop->BoostVector());
        pLeptonMinusBoosted->Boost(-pAntiTop->BoostVector());
        CosThetaPlus = cos(pLeptonPlusBoosted->Angle(pTopBoosted->Vect()));
        CosThetaMinus = cos(pLeptonMinusBoosted->Angle(pAntiTopBoosted->Vect()));

        pBBoosted->Boost(-pTop->BoostVector());
        pBbarBoosted->Boost(-pAntiTop->BoostVector());

        CosLeptonAngleD = cos(pLeptonPlusBoosted->Angle(pLeptonMinusBoosted->Vect()));

        double Nenner = 1 - 0.256*CosThetaPlus*CosThetaMinus;
        
        w_A = (-CosThetaPlus*CosThetaMinus)/Nenner;
        w_N = 1./Nenner;
        
        w_LL = (1-CosThetaPlus*CosThetaMinus-CosThetaPlus+CosThetaMinus)/Nenner;
        w_LR = (1+CosThetaPlus*CosThetaMinus-CosThetaPlus-CosThetaMinus)/Nenner;
        w_RR = (1-CosThetaPlus*CosThetaMinus+CosThetaPlus-CosThetaMinus)/Nenner;
        w_RL = (1+CosThetaPlus*CosThetaMinus+CosThetaPlus+CosThetaMinus)/Nenner;
        
        histogram__gen_A->Fill(CosThetaPlus, CosThetaMinus, w_A);
        histogram__gen_N->Fill(CosThetaPlus, CosThetaMinus, w_N);
        
        histogram__gen_LL->Fill(CosThetaPlus, CosThetaMinus, w_LL);
        histogram__gen_LR->Fill(CosThetaPlus, CosThetaMinus, w_LR);
        histogram__gen_RR->Fill(CosThetaPlus, CosThetaMinus, w_RR);
        histogram__gen_RL->Fill(CosThetaPlus, CosThetaMinus, w_RL);
        
        histogram__gen_Correlation->Fill(CosThetaPlus, CosThetaMinus);

        if(numberOfLeptons == 2) 
        {
            if(pLeptonMinus->Px() != 0) histogram__semilepton_BLeptonMinus->Fill( cos(pLeptonMinusBoosted->Angle(pBBoosted->Vect())) );
            if(pLeptonPlus->Px() != 0) histogram__semilepton_BLeptonPlus->Fill( cos(pLeptonPlusBoosted->Angle(pBbarBoosted->Vect())) );
        }

        numberOfJets = numberOfPatJets;
        if(numberOfPatLeptons>=2 && numberOfPatJets >=2)
        {

            RekoNu_Px = -10000;
            RekoNu_Py= -10000;
            RekoNu_Pz= -10000;
        
            RekoAntiNu_Px= -10000;
            RekoAntiNu_Py= -10000;
            RekoAntiNu_Pz= -10000;

            RekoTop_M = -10;
            RekoAntiTop_M = -10;
            RekoTop_Pt = -10;
            RekoAntiTop_Pt = -10;


            
            // REKO THETA 

            pBJet1->SetPxPyPzE(0.,0.,0.,0.);
            pBJet2->SetPxPyPzE(0.,0.,0.,0.);
            pRekoLeptonPlus->SetPxPyPzE(0.,0.,0.,0.);
            pRekoLeptonMinus->SetPxPyPzE(0.,0.,0.,0.);
            pBJet->SetPxPyPzE(0.,0.,0.,0.);
            pBbarJet->SetPxPyPzE(0.,0.,0.,0.);
            pRekoNu->SetPxPyPzE(0.,0.,0.,-10000.);
            pRekoAntiNu->SetPxPyPzE(0.,0.,0.,-10000.);

            pBestNu->SetPxPyPzE(0.,0.,0.,-10000.);
            pBestAntiNu->SetPxPyPzE(0.,0.,0.,-10000.);
            pRekoNu1->SetPxPyPzE(0.,0.,0.,-10000.);
            pRekoAntiNu1->SetPxPyPzE(0.,0.,0.,-10000.);
            pRekoNu2->SetPxPyPzE(0.,0.,0.,-10000.);
            pRekoAntiNu2->SetPxPyPzE(0.,0.,0.,-10000.);

            int LeptonIndex[20];
            int BTagTrkCountIndex[50];
            int BTagSVsimpleIndex[50];
            int BTagSVcombIndex[50];
            int BJetsEIndex[50];
            int BJetDeltaRIndex[50];
            int BbarJetDeltaRIndex[50];
            TMath::Sort(20,PatLeptonsE,LeptonIndex);
            TMath::Sort(50,PatJetsBTag_TrkCount, BTagTrkCountIndex);
            TMath::Sort(50,PatJetsBTag_SVsimple, BTagSVsimpleIndex);
            TMath::Sort(50,PatJetsBTag_SVcomb, BTagSVcombIndex);
            TMath::Sort(50, PatJetsE, BJetsEIndex);
            TMath::Sort(50, PatJetsBQuarkDeltaR, BJetDeltaRIndex);
            TMath::Sort(50, PatJetsBbarQuarkDeltaR, BbarJetDeltaRIndex);


            // Leptonen auswaehlen
            int OtherLepton = -1;
            for(int j=0; PatLeptonsCharge[LeptonIndex[0]]==PatLeptonsCharge[LeptonIndex[j]] && j<20; j++){
                OtherLepton=j+1;
            }
//            if(PatLeptonsCharge[LeptonIndex[OtherLepton]]==0) std::cout<<"Only Leptons of same Charge in Event " << iEvent << "!!"<<std::endl;

            if(PatLeptonsCharge[LeptonIndex[OtherLepton]]!=0){
                // Leptonen zuordnen
                if(PatLeptonsCharge[LeptonIndex[0]]==-1){	
                    pRekoLeptonMinus->SetPxPyPzE(PatLeptonsPx[LeptonIndex[0]], PatLeptonsPy[LeptonIndex[0]], PatLeptonsPz[LeptonIndex[0]], PatLeptonsE[LeptonIndex[0]] );
                }

                if(PatLeptonsCharge[LeptonIndex[0]]==+1){	
                    pRekoLeptonPlus->SetPxPyPzE(PatLeptonsPx[LeptonIndex[0]], PatLeptonsPy[LeptonIndex[0]], PatLeptonsPz[LeptonIndex[0]], PatLeptonsE[LeptonIndex[0]] );
                }
            
                if(PatLeptonsCharge[LeptonIndex[OtherLepton]]==-1){	
                    pRekoLeptonMinus->SetPxPyPzE(PatLeptonsPx[LeptonIndex[OtherLepton]], PatLeptonsPy[LeptonIndex[OtherLepton]], PatLeptonsPz[LeptonIndex[OtherLepton]],PatLeptonsE[LeptonIndex[OtherLepton]] );
                }
           
                if(PatLeptonsCharge[LeptonIndex[OtherLepton]]==+1){	
                    pRekoLeptonPlus->SetPxPyPzE(PatLeptonsPx[LeptonIndex[OtherLepton]], PatLeptonsPy[LeptonIndex[OtherLepton]], PatLeptonsPz[LeptonIndex[OtherLepton]], PatLeptonsE[LeptonIndex[OtherLepton]] );
                }

                //cout << "Leptonen ausgewaehlt" << endl;

                Lepton_Mass = ((*pRekoLeptonPlus) + (*pRekoLeptonMinus)).M();

                if( TMath::Abs( Lepton_Mass - 90.0 ) > 10 || PatLeptonsPdgId[LeptonIndex[0]] + PatLeptonsPdgId[LeptonIndex[OtherLepton]] !=0 )
                {

                    double JetDisc[50];
                    numberOfGoodJets = 0;
                    for(int j=0; j<50; j++){
                        JetDisc[j] = 0.;
                        if(j<numberOfPatJets){
                            //JetDisc[j] = PatJetsBTag_TrkCount[j] * PatJetsEt[j];
                            if(PatJetsBTag_TrkCount[j]>1. && PatJetsEt[j]>20){
                                pJet[j]->SetPxPyPzE(PatJetsPx[j],PatJetsPy[j],  PatJetsPz[j], PatJetsE[j]);
                                if(TMath::Min(pJet[j]->Angle(pRekoLeptonPlus->Vect()), pJet[j]->Angle(pRekoLeptonMinus->Vect())) >0.1){
                                    numberOfGoodJets++;
                                    JetDisc[j] = PatJetsBTag_TrkCount[j] * PatJetsEt[j];
                                }
                            }
                            if(j<numberOfPatLeptons){
                                histogram__LeptonRelIso->Fill(PatLeptonsPt[j]/(PatLeptonsPt[j]+PatLeptonsTrkIso[j]+PatLeptonsCaloIso[j]));
                            }
                        }
                    }
                    int JetDiscIndex[50];
                    TMath::Sort(50, JetDisc, JetDiscIndex);
                        
                    // Jets auswaehlen
                    // verbesserte Auswahl (BTag*ET)
                    pBJet1->SetPxPyPzE(PatJetsPx[JetDiscIndex[0]],PatJetsPy[JetDiscIndex[0]],PatJetsPz[JetDiscIndex[0]],PatJetsE[JetDiscIndex[0]]);
                    pBJet2->SetPxPyPzE(PatJetsPx[JetDiscIndex[1]],PatJetsPy[JetDiscIndex[1]],PatJetsPz[JetDiscIndex[1]],PatJetsE[JetDiscIndex[1]]);

                    //pBJet1->SetPxPyPzE(PatJetsPx[BTagTrkCountIndex[0]],PatJetsPy[BTagTrkCountIndex[0]],PatJetsPz[BTagTrkCountIndex[0]],PatJetsE[BTagTrkCountIndex[0]]);
                    //pBJet2->SetPxPyPzE(PatJetsPx[BTagTrkCountIndex[1]],PatJetsPy[BTagTrkCountIndex[1]],PatJetsPz[BTagTrkCountIndex[1]],PatJetsE[BTagTrkCountIndex[1]]);
                    
                    
                    //cout << "Jets gewaehlt" << endl;
                    
                    
                    // Neutrinos berechnen 
                    
                    //Generator-Werte setzen fuer Vergleich mit Berechnung
                    pNu->SetPxPyPzE(pGenNu->Px(),pGenNu->Py(),pGenNu->Pz(),pGenNu->E());
                    pAntiNu->SetPxPyPzE(pGenAntiNu->Px(),pGenAntiNu->Py(),pGenAntiNu->Pz(),pGenAntiNu->E());
                    
                    
                    
                    Poly.Init(pRekoLeptonPlus, pRekoLeptonMinus, pBJet1, pBJet2, pNu, pAntiNu); // BJet1 = b, BJet2 = bbar
                    Poly.Solve(170.0,171.0 , iEvent, pRekoNu1, pRekoAntiNu1, pBestNu, pBestAntiNu);
                    
                    Poly.Init(pRekoLeptonPlus, pRekoLeptonMinus, pBJet2, pBJet1, pNu, pAntiNu); // BJet1 = bbar, BJet2 = b
                    Poly.Solve(170.0,171.0 , iEvent, pRekoNu2, pRekoAntiNu2, pBestNu2, pBestAntiNu2);
                    
                    //cout << "Neutrinos berechnet" << endl;
                    
                    
// Abfrage, ob Neutrinoloesung ungleich -10000 !!!
                    if(pRekoAntiNu1->Pz() != -10000 && pRekoAntiNu2->Pz() != -10000){
                        
                        if(TMath::Abs( ((*pRekoLeptonPlus)+(*pRekoNu1)+(*pBJet1)).M() + ((*pRekoLeptonMinus)+(*pRekoAntiNu1)+(*pBJet2)).M() - 2*173.2) < TMath::Abs(((*pRekoLeptonPlus)+(*pRekoNu2)+(*pBJet2)).M() + ((*pRekoLeptonMinus)+(*pRekoAntiNu2)+(*pBJet1)).M() - 2*173.2) ){
                            *pBJet = *pBJet1;
                            *pBbarJet = *pBJet2;
                            *pRekoNu = *pRekoNu1;
                            *pRekoAntiNu = *pRekoAntiNu1;
                        }
                        else {
                            *pBJet = *pBJet2;
                            *pBbarJet = *pBJet1;
                            *pRekoNu = *pRekoNu2;
                            *pRekoAntiNu = *pRekoAntiNu2;
                            *pBestNu = *pBestNu2;
                            *pBestAntiNu = *pBestAntiNu2;
                        }
                    }
                    else if(pRekoAntiNu1->Pz() != -10000){
                        *pBJet = *pBJet1;
                        *pBbarJet = *pBJet2;
                        *pRekoNu = *pRekoNu1;
                        *pRekoAntiNu = *pRekoAntiNu1;
                    }
                    else if(pRekoAntiNu2->Pz() != -10000){
                        *pBJet = *pBJet2;
                        *pBbarJet = *pBJet1;
                        *pRekoNu = *pRekoNu2;
                        *pRekoAntiNu = *pRekoAntiNu2;
                        *pBestNu = *pBestNu2;
                        *pBestAntiNu = *pBestAntiNu2;
                    }
                    else{
                        pRekoNu->SetPxPyPzE(0,0,-10000, 10000);
                        pRekoAntiNu->SetPxPyPzE(0,0,-10000, 10000);
                        pBestNu->SetPxPyPzE(0,0,-10000, 10000);
                        pBestAntiNu->SetPxPyPzE(0,0,-10000, 10000);
                        pBJet->SetPxPyPzE(0,0,-10000, 10000);
                        pBbarJet->SetPxPyPzE(0,0,-10000, 10000);
                    }
                    
                    
                    
                    TTbar_Pt = pTTbar->Pt();
                    TTbar_M = pTTbar->M();
                    
                    Top_Pt = pTop->Pt();
                    AntiTop_Pt = pAntiTop->Pt();
                    Top_M = pTop->M();
                    AntiTop_M = pAntiTop->M();
                    
                    Nu_Px = pNu->Px();
                    Nu_Py = pNu->Py();
                    Nu_Pz = pNu->Pz();
                    
                    AntiNu_Px = pAntiNu->Px();
                    AntiNu_Py = pAntiNu->Py();
                    AntiNu_Pz = pAntiNu->Pz();
                    
                    
                    
                    Lepton_Pt = TMath::Min(pRekoLeptonPlus->Pt(), pRekoLeptonMinus->Pt());
                    BJet_Et = TMath::Min(pBJet->Et(), pBbarJet->Et());
                    BJet_Tag_SVsimple = PatJetsBTag_SVsimple[BTagSVsimpleIndex[1]];
                    BJet_Tag_SVcomb = PatJetsBTag_SVcomb[BTagSVcombIndex[1]];
                    BJet_Tag_TrkCount = PatJetsBTag_TrkCount[BTagTrkCountIndex[1]];
                    BJet_Disc = JetDisc[JetDiscIndex[1]];
                    Lepton1_Id = PatLeptonsPdgId[LeptonIndex[0]];
                    Lepton2_Id = PatLeptonsPdgId[LeptonIndex[OtherLepton]];
                    
                    LeptonPlus_Angle = -10.;
                    LeptonMinus_Angle = -10.;
                    BJet_Angle = -10.;
                    BbarJet_Angle = -10.;
                    RekoNu_Angle = -10.;
                    RekoAntiNu_Angle = -10.;
                    BestNu_Angle = -10.;
                    BestAntiNu_Angle = -10.;
                    
                    //cout << "Werte gesetzt" << endl;
                    
                    if(pRekoAntiNu->Pz() > -10000){

                        histogram_nupx_gen_reco->Fill(pGenNu->Px(), pRekoNu->Px());
                        histogram_nubpx_gen_reco->Fill(pGenAntiNu->Px(), pRekoAntiNu->Px());
                        histogram_nupy_gen_reco->Fill(pGenNu->Py(), pRekoNu->Py());
                        histogram_nubpy_gen_reco->Fill(pGenAntiNu->Py(), pRekoAntiNu->Py());
                        histogram_nupz_gen_reco->Fill(pGenNu->Pz(), pRekoNu->Pz());
                        histogram_nubpz_gen_reco->Fill(pGenAntiNu->Pz(), pRekoAntiNu->Pz());
                        
                        if(pLeptonPlus->E() != 0 && pLeptonMinus->E() != 0 && pBQuark->E() != 0 ){
                            BJet_Angle = pBJet->DeltaR(*pBQuark);
                            BbarJet_Angle = pBbarJet->DeltaR(*pBbarQuark);
                            LeptonPlus_Angle = pRekoLeptonPlus->DeltaR(*pLeptonPlus);
                            LeptonMinus_Angle = pRekoLeptonMinus->DeltaR(*pLeptonMinus);
                            RekoNu_Angle = pRekoNu->DeltaR(*pNu);
                            RekoAntiNu_Angle = pRekoAntiNu->DeltaR(*pAntiNu);
                            BestNu_Angle = pBestNu->DeltaR(*pNu);
                            BestAntiNu_Angle = pBestAntiNu->DeltaR(*pAntiNu);
                        }

                        RekoNu_Px = pRekoNu->Px();
                        RekoNu_Py = pRekoNu->Py();
                        RekoNu_Pz = pRekoNu->Pz();
                        
                        RekoAntiNu_Px = pRekoAntiNu->Px();
                        RekoAntiNu_Py = pRekoAntiNu->Py();
                        RekoAntiNu_Pz = pRekoAntiNu->Pz();
                        
                        BestNu_Px = pBestNu->Px();
                        BestNu_Py = pBestNu->Py();
                        BestNu_Pz = pBestNu->Pz();
                        
                        BestAntiNu_Px = pBestAntiNu->Px();
                        BestAntiNu_Py = pBestAntiNu->Py();
                        BestAntiNu_Pz = pBestAntiNu->Pz(); 
                        
                        if(pRekoLeptonPlus->E()!=0 && pRekoLeptonMinus->E()!=0 && pBJet->E()!=0 && pBbarJet->E()!=0){ 
                            
                            EventIsGood = 1;
                            
                            *pRekoTop = (*pRekoLeptonPlus) + (*pBJet) + (*pRekoNu);
                            *pRekoAntiTop = (*pRekoLeptonMinus) + (*pBbarJet) + (*pRekoAntiNu);
                            *pRekoTTbar = (*pRekoTop) + (*pRekoAntiTop);
                            *pRekoTopBoosted = *pRekoTop;
                            *pRekoAntiTopBoosted = *pRekoAntiTop;
                            *pRekoLeptonPlusBoosted = *pRekoLeptonPlus;
                            *pRekoLeptonMinusBoosted = *pRekoLeptonMinus;
                            pRekoAntiTopBoosted->Boost(-pRekoTTbar->BoostVector());
                            pRekoTopBoosted->Boost(-pRekoTTbar->BoostVector());
                            pRekoLeptonPlusBoosted->Boost(-pRekoTop->BoostVector());
                            pRekoLeptonMinusBoosted->Boost(-pRekoAntiTop->BoostVector());
                            
                            RekoCosThetaPlus = cos(pRekoLeptonPlusBoosted->Angle(pRekoTopBoosted->Vect()));
                            RekoCosThetaMinus = cos(pRekoLeptonMinusBoosted->Angle(pRekoAntiTopBoosted->Vect()));
                            //cout << "Cos(Theta) Gen-Reko: " << CosThetaPlus - RekoCosThetaPlus << endl;
                            
                            CosThetaDiff = RekoCosThetaPlus - CosThetaPlus;

                            CosRekoLeptonAngleD = cos(pRekoLeptonPlusBoosted->Angle(pRekoLeptonMinusBoosted->Vect()));
                            
                            RekoTTbar_Pt = pRekoTTbar->Pt();
                            RekoTTbar_M = pRekoTTbar->M();
                            
                            RekoTop_Pt = pRekoTop->Pt();
                            RekoAntiTop_Pt = pRekoAntiTop->Pt();
                            
                            RekoTop_M = pRekoTop->M();
                            RekoAntiTop_M = pRekoAntiTop->M();
                            
                            
                            
                            histogram__A->Fill(RekoCosThetaPlus, RekoCosThetaMinus, w_A);
                            histogram__N->Fill(RekoCosThetaPlus, RekoCosThetaMinus, w_N);
                            
                            histogram__Correlation->Fill(RekoCosThetaPlus, RekoCosThetaMinus);
                            
                            histogram__CosThetaDiff->Fill( CosThetaPlus - RekoCosThetaPlus );
                            histogram__CosThetaDiff->Fill( CosThetaMinus - RekoCosThetaMinus );
                            histogram__CosTheta_GenReko->Fill(CosThetaPlus, RekoCosThetaPlus);
                            
                            histogram__CosThetaDiff_TTbarPt->Fill(pTTbar->Pt(), CosThetaPlus - RekoCosThetaPlus);

                            if(BJet_Tag_TrkCount > 1.0){
                                histogram__Correlation_T1->Fill(RekoCosThetaPlus, RekoCosThetaMinus);
                                histogram__A_T1->Fill(RekoCosThetaPlus, RekoCosThetaMinus, w_A);
                                histogram__N_T1->Fill(RekoCosThetaPlus, RekoCosThetaMinus, w_N);
                            }


                            if(pRekoLeptonPlus->Pt()>15 && pRekoLeptonMinus->Pt()>15 && pBJet->Et()>50 && pBbarJet->Et()>50 && PatJetsBTag_TrkCount[BTagTrkCountIndex[1]]>1 ){
                                histogram__Correlation_L15_B50_T1->Fill(RekoCosThetaPlus, RekoCosThetaMinus);
                                histogram__A_L15_B50_T1->Fill(RekoCosThetaPlus, RekoCosThetaMinus, w_A);
                                histogram__N_L15_B50_T1->Fill(RekoCosThetaPlus, RekoCosThetaMinus, w_N);

                            }
                            if(pRekoLeptonPlus->Pt()>20 && pRekoLeptonMinus->Pt()>20){
                                    
                                histogram__Correlation_L20->Fill(RekoCosThetaPlus, RekoCosThetaMinus);
                                histogram__A_L20->Fill(RekoCosThetaPlus, RekoCosThetaMinus, w_A);
                                histogram__N_L20->Fill(RekoCosThetaPlus, RekoCosThetaMinus, w_N);

                                if(pBJet->Et() > 30 && pBbarJet->Et() > 30 && PatJetsBTag_TrkCount[BTagTrkCountIndex[1]] > 1){
                                    histogram__Correlation_L20_B30_T1->Fill(RekoCosThetaPlus, RekoCosThetaMinus);
                                    histogram__A_L20_B30_T1->Fill(RekoCosThetaPlus, RekoCosThetaMinus, w_A);
                                    histogram__N_L20_B30_T1->Fill(RekoCosThetaPlus, RekoCosThetaMinus, w_N);
                                }
                                    
                                if(pBJet->Et() > 40 && pBbarJet->Et() > 40){
                                    histogram__Correlation_L20_B40->Fill(RekoCosThetaPlus, RekoCosThetaMinus);
                                    histogram__A_L20_B40->Fill(RekoCosThetaPlus, RekoCosThetaMinus, w_A);
                                    histogram__N_L20_B40->Fill(RekoCosThetaPlus, RekoCosThetaMinus, w_N);
                                        
                                    if(PatJetsBTag_TrkCount[BTagTrkCountIndex[1]] > 1 ){
                                        histogram__Correlation_L20_B40_T1->Fill(RekoCosThetaPlus, RekoCosThetaMinus);
                                        histogram__A_L20_B40_T1->Fill(RekoCosThetaPlus, RekoCosThetaMinus, w_A);
                                        histogram__N_L20_B40_T1->Fill(RekoCosThetaPlus, RekoCosThetaMinus, w_N);
                                    }
                                }
                            }
                        } // Leptonen und B != 0
                    } // Neutrino-Pz != -10000
                } // inv. Masse der Leptonen != Z-Masse+-10
            }// abfrage auf 2 Leptonen unterschiedlicher Ladung
            //cout << "Tree wird gefuellt: ";
  
            //cout << " und ist fertig" << endl;
            
        }
        outTree->Fill(); 
    } // EventLoop

    cout << "gezaehlte Ereignisse: " << EventCounter << endl;
    cout << "Rekonstruierte Ereignisse: " << histogram__Correlation->Integral() << endl;
    

    outputFile->cd("");
    outputFile->Write();
    outputFile->Close();
    delete outputFile;
}
void number_of_particles_leaving_GEM_hits_boxgen(TString pre="", int nevts=0, double mom=4.1){
	  TDatabasePDG::Instance()-> AddParticle("pbarpSystem","pbarpSystem", 1.9, kFALSE, 0.1, 0,"", 88888);

	  TStopwatch timer;

	  if (pre==""){
		  //Output File
		  TString OutputFile = "test_analysis_output.root";
		  TString outPath = "";
		  //Input simulation Files
		 TString inPIDFile = "pid_complete.root";
		 TString inParFile = "simparams.root";
	  }
	  else {
		  //Output File
		  TString outPath = pre + "_";
		  TString OutputFile = pre + "_test_analysis_output.root";

		  //Input simulation Files
		  TString inPIDFile = pre + "_pid_complete.root";
		  TString inParFile = pre + "_simparams.root";
	  }

	  TString PIDParFile = TString( gSystem->Getenv("VMCWORKDIR")) + "/macro/params/all.par";

	  //Initialization
	  FairLogger::GetLogger()->SetLogToFile(kFALSE);
	  FairRunAna* RunAna = new FairRunAna();
	  FairRuntimeDb* rtdb = RunAna->GetRuntimeDb();
	  RunAna->SetInputFile(inPIDFile);

	  //setup parameter database
	  FairParRootFileIo* parIo = new FairParRootFileIo();
	  parIo->open(inParFile);
	  FairParAsciiFileIo* parIoPID = new FairParAsciiFileIo();
	  parIoPID->open(PIDParFile.Data(),"in");

	  rtdb->setFirstInput(parIo);
	  rtdb->setSecondInput(parIoPID);
	  rtdb->setOutput(parIo);

	  RunAna->SetOutputFile(OutputFile);
	  RunAna->Init();


	  /*************************************************************************
	   *  Create new ntuple and fill them with information
	   ************************************************************************/

	  //*** create tuples
	  RhoTuple * ntpPiMinus = new RhoTuple("ntpPiMinus", "PiMinus info");
	  RhoTuple * ntpPiPlus = new RhoTuple("ntpPiPlus", "PiPlus info");
	  RhoTuple * ntpKaonMinus = new RhoTuple("ntpKaonMinus", "KaonMinus info");
	  RhoTuple * ntpKaonPlus = new RhoTuple("ntpKaonPlus", "KaonPlus info");
	  RhoTuple * ntpProton = new RhoTuple("ntpProton", "Proton info");
	  RhoTuple * ntpAntiProton = new RhoTuple("ntpAntiProton", "Antiproton info");


	  //Create output file
	  TFile *out = TFile::Open(outPath+"test_output_ana.root","RECREATE");

	  // data reader Object
	  PndAnalysis* theAnalysis = new PndAnalysis();
	  if (nevts==0) nevts = theAnalysis->GetEntries();


	  //RhoCandLists for analysis
	  RhoCandList piplus, piminus, proton, antiproton, kaonminus, kaonplus;

	  RhoCandidate * dummyCand = new RhoCandidate(); //dummy candidate for empty candidate usage


	  double p_m0 = TDatabasePDG::Instance()->GetParticle("proton")->Mass();


	  TLorentzVector ini (0,0, mom, sqrt(p_m0*p_m0+ mom*mom)+p_m0);
	  TVector3 beamBoost = ini.BoostVector();

	  PndRhoTupleQA qa(theAnalysis, mom);

	  int evt=-1;
	  while (theAnalysis->GetEvent() && ++evt<nevts){

	    if ((evt%100)==0) cout << "evt "<< evt <<endl;


	    TString PidSelection = "PidAlgoIdealCharged";//"PidAlgoMvd;PidAlgoStt;PidAlgoDrc"; to change from ideal PID to realistic PID uncomment this!


	    //***Selection with no PID info
	    theAnalysis->FillList(piminus, "PionBestMinus", PidSelection);
	    theAnalysis->FillList(piplus, "PionBestPlus", PidSelection);
	    theAnalysis->FillList(kaonminus, "KaonBestMinus", PidSelection);
	    theAnalysis->FillList(kaonplus, "KaonBestPlus", PidSelection);
	    theAnalysis->FillList(proton, "ProtonBestPlus", PidSelection);
	    theAnalysis->FillList(antiproton, "ProtonBestMinus", PidSelection);


	    //Get piminus information
	    ntpPiMinus->Column("ev",     (Float_t) evt);

	    for (int j=0; j<piminus.GetLength(); ++j){


			//information about the mother and MCTruth Candidate

			TLorentzVector l;
			float costheta = -999.;

			RhoCandidate * truth = piminus[j]->GetMcTruth();
			RhoCandidate * mother;
			if (truth)  mother = truth->TheMother();

			int moth = (mother==0x0) ? 88888 : mother->PdgCode();
			ntpPiMinus->Column("Mother", (Int_t) moth);

			bool truthmatch = theAnalysis->McTruthMatch(piminus[j]);
			ntpPiMinus->Column("MCTruthMatch", (bool) truthmatch);

			int gemhit = GemHits(piminus[j]);

			int count = 0;
			if (moth==88888 && gemhit==1 && truthmatch==1) count=1;

			ntpPiMinus->Column("GemHit", (int) count, 0);


	    }
	    ntpPiMinus->DumpData();

		//Get PiPlus information

	    ntpPiPlus->Column("ev", (int) evt);

	    for (int j=0; j<piplus.GetLength(); ++j){


			//information about the mother and MCTruth Candidate

			TLorentzVector l;
			float costheta = -999.;

			RhoCandidate * truth = piplus[j]->GetMcTruth();
			RhoCandidate * mother;
			if (truth)  mother = truth->TheMother();

			int moth = (mother==0x0) ? 88888 : mother->PdgCode();
			ntpPiPlus->Column("Mother", (Int_t) moth);

			bool truthmatch = theAnalysis->McTruthMatch(piplus[j]);
			ntpPiPlus->Column("MCTruthMatch", (bool) truthmatch);

			int gemhit = GemHits(piplus[j]);

			int count = 0;
			if (moth==88888 && gemhit==1 && truthmatch==1) count=1;

			ntpPiPlus->Column("GemHit", (int) count, 0);


	    }

	    ntpPiPlus->DumpData();

	    ntpKaonMinus->Column("ev", (int) evt);

	    for (int j=0; j<kaonminus.GetLength(); ++j){


			//information about the mother and MCTruth Candidate

			TLorentzVector l;
			float costheta = -999.;

			RhoCandidate * truth = kaonminus[j]->GetMcTruth();
			RhoCandidate * mother;
			if (truth)  mother = truth->TheMother();

			int moth = (mother==0x0) ? 88888 : mother->PdgCode();
			ntpKaonMinus->Column("Mother", (Int_t) moth);

			bool truthmatch = theAnalysis->McTruthMatch(kaonminus[j]);
			ntpKaonMinus->Column("MCTruthMatch", (bool) truthmatch);

			int gemhit = GemHits(kaonminus[j]);

			int count = 0;
			if (moth==88888 && gemhit==1 && truthmatch==1) count=1;

			ntpKaonMinus->Column("GemHit", (int) count, 0);


	    }

	    ntpKaonMinus->DumpData();


	    ntpKaonPlus->Column("ev", (int) evt);

	    for (int j=0; j<kaonplus.GetLength(); ++j){


			//information about the mother and MCTruth Candidate

			TLorentzVector l;
			float costheta = -999.;

			RhoCandidate * truth = kaonplus[j]->GetMcTruth();
			RhoCandidate * mother;
			if (truth)  mother = truth->TheMother();

			int moth = (mother==0x0) ? 88888 : mother->PdgCode();
			ntpKaonPlus->Column("Mother", (Int_t) moth);

			bool truthmatch = theAnalysis->McTruthMatch(kaonplus[j]);
			ntpKaonPlus->Column("MCTruthMatch", (bool) truthmatch);

			int gemhit = GemHits(kaonplus[j]);

			int count = 0;
			if (moth==88888 && gemhit==1 && truthmatch==1) count=1;

			ntpKaonPlus->Column("GemHit", (int) count, 0);


	    }

	    ntpKaonPlus->DumpData();

//		Get Proton information
	    ntpProton->Column("ev", (int) evt);

	    for (int j=0; j<proton.GetLength(); ++j){


			//information about the mother and MCTruth Candidate

			TLorentzVector l;
			float costheta = -999.;

			RhoCandidate * truth = proton[j]->GetMcTruth();
			RhoCandidate * mother;
			if (truth)  mother = truth->TheMother();

			int moth = (mother==0x0) ? 88888 : mother->PdgCode();
			ntpProton->Column("Mother", (Int_t) moth);

			bool truthmatch = theAnalysis->McTruthMatch(proton[j]);
			ntpProton->Column("MCTruthMatch", (bool) truthmatch);

			int gemhit = GemHits(proton[j]);

			int count = 0;
			if (moth==88888 && gemhit==1 && truthmatch==1) count=1;

			ntpProton->Column("GemHit", (int) count, 0);


	    }

	    ntpProton->DumpData();

//			Get Antiproton
	    ntpAntiProton->Column("ev", (int) evt);

	    for (int j=0; j<antiproton.GetLength(); ++j){


			//information about the mother and MCTruth Candidate

			TLorentzVector l;
			float costheta = -999.;

			RhoCandidate * truth = antiproton[j]->GetMcTruth();
			RhoCandidate * mother;
			if (truth)  mother = truth->TheMother();

			int moth = (mother==0x0) ? 88888 : mother->PdgCode();
			ntpAntiProton->Column("Mother", (Int_t) moth);

			bool truthmatch = theAnalysis->McTruthMatch(antiproton[j]);
			ntpAntiProton->Column("MCTruthMatch", (bool) truthmatch);

			int gemhit = GemHits(antiproton[j]);

			int count = 0;
			if (moth==88888 && gemhit==1 && truthmatch==1) count=1;

			ntpAntiProton->Column("GemHit", (int) count, 0);


	    }

	    ntpAntiProton->DumpData();

	  }


	  //Write output
	  out->cd();

	  ntpPiMinus ->GetInternalTree()->Write();
	  ntpPiPlus->GetInternalTree()->Write();
	  ntpKaonMinus ->GetInternalTree()->Write();
	  ntpKaonPlus->GetInternalTree()->Write();
	  ntpProton->GetInternalTree()->Write();
	  ntpAntiProton->GetInternalTree()->Write();


	  out->Save();

	  timer.Stop();
	  Double_t rtime = timer.RealTime();
	  Double_t ctime = timer.CpuTime();

	  cout<<"Macro finisched successfully."<<endl;
	  cout<<"Realtime: "<<rtime<<" s, CPU time: "<<ctime<<" s"<<endl;
	  cout<<endl;


	  exit(0);

	}
// Get corrections from table
float qq2vvEWKcorrections::getqq2WWEWKCorr(
                       float ptl1 , float etal1 , float phil1 , float idl1 , // lepton from 1st W
                       float ptl2 , float etal2 , float phil2 , float idl2 , // lepton from 2nd W
                       float ptv1 , float etav1 , float phiv1 ,             // neutrino from 1st W
                       float ptv2 , float etav2 , float phiv2 ,             // neutrino from 2nd W
                       float x1   , float x2 ,                              // parton x-Bjorken
                       float id1  , float id2                               // parton PDG id's
//                       int   TypeFirst = 1 ,                                // ??????????????????????????
//                        float Energy = 8000.
                     ) {

 float Energy = 8000.;
 // Create lepton and neutrino vectors
 TLorentzVector l1;
 TLorentzVector l2;
 TLorentzVector v1;
 TLorentzVector v2;

 float me   = 0.001*0.510998928 ;
 float mmu  = 0.001*105.6583715 ;
 float mtau = 0.001*1776.82     ;

 float ml1(0) , ml2(0) ;

 if      ( idl1 == 11 ) ml1 = me   ;
 else if ( idl1 == 13 ) ml1 = mmu  ;
 else if ( idl1 == 15 ) ml1 = mtau ;
 if      ( idl2 == 11 ) ml2 = me   ;
 else if ( idl2 == 13 ) ml2 = mmu  ;
 else if ( idl2 == 15 ) ml2 = mtau ;

 l1.SetPtEtaPhiM(ptl1,etal1,phil1,ml1);
 l2.SetPtEtaPhiM(ptl2,etal2,phil2,ml2);
 v1.SetPtEtaPhiM(ptv1,etav1,phiv1,0.0);
 v2.SetPtEtaPhiM(ptv2,etav2,phiv2,0.0);

 TLorentzVector W1 = l1+v1; // W1
 TLorentzVector W2 = l2+v2; // W2
 TLorentzVector WW = W1+W2;

 //---- FIX
 //---- swap 1 <->2 for leptons and neutrinos, to get correctly association l-v:
 //---- use as test invariatn mass of di-leptons
 //----    needed because leptons are ordered by "pt" and not by "mother" in the input! 
 if ((W1.M() - 80.385) > 0.1 && (W2.M() - 80.385) > 0.1) {
  W1 = l1+v2; // W1
  W2 = l2+v1; // W2
  WW = W1+W2;
 }
 //---- end FIX


 float M_12   = 80.385 , M_22 = 80.385 ;

 TLorentzVector p1; p1.SetPxPyPzE(0.,0.,Energy*x1,Energy*x1);
 TLorentzVector p2; p2.SetPxPyPzE(0.,0.,-Energy*x2,Energy*x2);

 //S-HAT
 float s_hat = pow(WW.E(),2)-pow(WW.Px(),2)-pow(WW.Py(),2)-pow(WW.Pz(),2); // ScalarProd(WW) (p1+p2)^2 = (p3+p4)^2 ~ +2*p1*p2
  //T_HAT
  //float t_hat2 = TypeFirst == 1 ? p1.M()*p1.M() + M_12*M_12 - 2*( p1.E()*W1.E() - p1.Px()*W1.Px() - p1.Py()*W1.Py() - p1.Pz()*W1.Pz() ) :
  //                                p1.M()*p1.M() + M_22*M_22 - 2*( p1.E()*W2.E() - p1.Px()*W2.Px() - p1.Py()*W2.Py() - p1.Pz()*W2.Pz() )   ; //T_HAT LO
 float la1 = sqrt( pow(s_hat,2) );            //la = sqrt( pow(a,2)+pow(b,2)+pow(c,2)-2*(a*b+a*c+b*c) );
 float la2 = sqrt( pow(s_hat,2) + pow(M_12,2) + pow(M_22,2) - 2*(s_hat*M_12 + s_hat*M_22 + M_12*M_22) );
  //  Boost: boost ext. momenta in CM frame of W1,W2
 TLorentzVector W1_b = W1, W2_b = W2;
 TLorentzVector p1_b = p1, p2_b = p2;
 W1_b.Boost( -WW.BoostVector() );
 W2_b.Boost( -WW.BoostVector() );
 p1_b.Boost( -WW.BoostVector() );
 p2_b.Boost( -WW.BoostVector() );

 //  Uni-vector
 TLorentzVector ee1 = p1_b*(1./sqrt( pow(p1_b.X(),2)+pow(p1_b.Y(),2)+pow(p1_b.Z(),2) ));
 TLorentzVector ee2 = p2_b*(1./sqrt( pow(p2_b.X(),2)+pow(p2_b.Y(),2)+pow(p2_b.Z(),2) ));
 TLorentzVector z1  = W1_b*(1./sqrt( pow(W1_b.X(),2)+pow(W1_b.Y(),2)+pow(W1_b.Z(),2) ));
 TLorentzVector z2  = W2_b*(1./sqrt( pow(W2_b.X(),2)+pow(W2_b.Y(),2)+pow(W2_b.Z(),2) ));
 //  "effective" beam axis
 float abse = sqrt( pow(ee1.X()-ee2.X(),2) + pow(ee1.Y()-ee2.Y(),2) + pow(ee1.Z()-ee2.Z(),2) );
 TLorentzVector ee = (ee1-ee2) * (1. / abse);
  //  "effective" scattering angle
 float costh = ee.X()*z1.X()+ee.Y()*z1.Y()+ee.Z()*z1.Z();
  //  final T_HAT
 float t_hat= M_12 - (1./2.)*(s_hat+M_12-M_22) + (1/(2*s_hat))*la1*la2*costh; //Mz-1/2*s+1/(2*s)*la(s,0,0)*la(s,mZ,mZ)*costh  or: (p1-p3)^2 = (p2-p4)^2 ~ -2*p1*p3
  //Quark Type
 int quarkType = -1.;
 if(      fabs(id1)==2 && fabs(id2)==2 ) quarkType=0; //delta_uub
 else if( fabs(id1)==1 && fabs(id2)==1 ) quarkType=1; //delta_ddb
 else if( fabs(id1)==5 && fabs(id2)==5 ) quarkType=2; //delta_bbb
 else if( fabs(id1)==4 && fabs(id2)==4 ) quarkType=0; // cc as delta_buu
 else if( fabs(id1)==3 && fabs(id2)==3 ) quarkType=1; // ss as delta_bdd

 // Extracting corrections
 float EWK_w = 1. ;
//  std::cout << " quarkType = " << quarkType << " id1 = " << id1 << " id2 = " << id2 << std::endl;
 if( quarkType!=-1 ){
  float sqrt_s_hat = sqrt(s_hat);
  std::vector<std::vector<float> > EWK_w2_vec = findCorrection( sqrt_s_hat, t_hat );
  float EWK_w2 = 1. + EWK_w2_vec[0][quarkType];
  EWK_w = EWK_w2;
 }

 return EWK_w ;

}
Exemple #14
0
inline TVector3 kinematics::systemBoostVector( TLorentzVector* pa, TLorentzVector* pb )
{
	TLorentzVector pTmp = (*pa)+(*pb);
	return pTmp.BoostVector();
}
Exemple #15
0
void calculateAngles(TLorentzVector thep4H, TLorentzVector thep4Z1, TLorentzVector thep4Lep11, TLorentzVector thep4Lep12, TLorentzVector thep4Z2, TLorentzVector thep4Lep21, TLorentzVector thep4Lep22, double& costheta1, double& costheta2, double& phi, double& costhetastar, double& phistar1){
	
	
	//std::cout << "In calculate angles..." << std::endl;
	
	double norm;
	
	TVector3 boostX = -(thep4H.BoostVector());
	TLorentzVector thep4Z1inXFrame( thep4Z1 );
	TLorentzVector thep4Z2inXFrame( thep4Z2 );	
	thep4Z1inXFrame.Boost( boostX );
	thep4Z2inXFrame.Boost( boostX );
	TVector3 theZ1X_p3 = TVector3( thep4Z1inXFrame.X(), thep4Z1inXFrame.Y(), thep4Z1inXFrame.Z() );
	TVector3 theZ2X_p3 = TVector3( thep4Z2inXFrame.X(), thep4Z2inXFrame.Y(), thep4Z2inXFrame.Z() );
	
	///////////////////////////////////////////////
	// check for z1/z2 convention, redefine all 4 vectors with convention
	///////////////////////////////////////////////	
	TLorentzVector p4H, p4Z1, p4M11, p4M12, p4Z2, p4M21, p4M22;

	p4Z1 = thep4Z1; p4M11 = thep4Lep11; p4M12 = thep4Lep12;
	p4Z2 = thep4Z2; p4M21 = thep4Lep21; p4M22 = thep4Lep22;
	costhetastar = theZ1X_p3.CosTheta();
	
	// now helicity angles................................
	// ...................................................
	TVector3 boostZ1 = -(p4Z1.BoostVector());
	TLorentzVector p4Z2Z1(p4Z2);
	p4Z2Z1.Boost(boostZ1);
	//find the decay axis
	/////TVector3 unitx_1 = -Hep3Vector(p4Z2Z1);
	TVector3 unitx_1( -p4Z2Z1.X(), -p4Z2Z1.Y(), -p4Z2Z1.Z() );
	norm = 1/(unitx_1.Mag());
	unitx_1*=norm;
	//boost daughters of z2
	TLorentzVector p4M21Z1(p4M21);
	TLorentzVector p4M22Z1(p4M22);
	p4M21Z1.Boost(boostZ1);
	p4M22Z1.Boost(boostZ1);
	//create z and y axes
	/////TVector3 unitz_1 = Hep3Vector(p4M21Z1).cross(Hep3Vector(p4M22Z1));
	TVector3 p4M21Z1_p3( p4M21Z1.X(), p4M21Z1.Y(), p4M21Z1.Z() );
	TVector3 p4M22Z1_p3( p4M22Z1.X(), p4M22Z1.Y(), p4M22Z1.Z() );
	TVector3 unitz_1 = p4M21Z1_p3.Cross( p4M22Z1_p3 );
	norm = 1/(unitz_1.Mag());
	unitz_1 *= norm;
	TVector3 unity_1 = unitz_1.Cross(unitx_1);
	
	//caculate theta1
	TLorentzVector p4M11Z1(p4M11);
	p4M11Z1.Boost(boostZ1);
	TVector3 p3M11( p4M11Z1.X(), p4M11Z1.Y(), p4M11Z1.Z() );
	TVector3 unitM11 = p3M11.Unit();
	double x_m11 = unitM11.Dot(unitx_1); double y_m11 = unitM11.Dot(unity_1); double z_m11 = unitM11.Dot(unitz_1);
	TVector3 M11_Z1frame(y_m11, z_m11, x_m11);
	costheta1 = M11_Z1frame.CosTheta();
	//std::cout << "theta1: " << M11_Z1frame.Theta() << std::endl;
	//////-----------------------old way of calculating phi---------------/////////
	phi = M11_Z1frame.Phi();
	
	//set axes for other system
	TVector3 boostZ2 = -(p4Z2.BoostVector());
	TLorentzVector p4Z1Z2(p4Z1);
	p4Z1Z2.Boost(boostZ2);
	TVector3 unitx_2( -p4Z1Z2.X(), -p4Z1Z2.Y(), -p4Z1Z2.Z() );
	norm = 1/(unitx_2.Mag());
	unitx_2*=norm;
	//boost daughters of z2
	TLorentzVector p4M11Z2(p4M11);
	TLorentzVector p4M12Z2(p4M12);
	p4M11Z2.Boost(boostZ2);
	p4M12Z2.Boost(boostZ2);
	TVector3 p4M11Z2_p3( p4M11Z2.X(), p4M11Z2.Y(), p4M11Z2.Z() );
	TVector3 p4M12Z2_p3( p4M12Z2.X(), p4M12Z2.Y(), p4M12Z2.Z() );
	TVector3 unitz_2 = p4M11Z2_p3.Cross( p4M12Z2_p3 );
	norm = 1/(unitz_2.Mag());
	unitz_2*=norm;
	TVector3 unity_2 = unitz_2.Cross(unitx_2);
	//calcuate theta2
	TLorentzVector p4M21Z2(p4M21);
	p4M21Z2.Boost(boostZ2);
	TVector3 p3M21( p4M21Z2.X(), p4M21Z2.Y(), p4M21Z2.Z() );
	TVector3 unitM21 = p3M21.Unit();
	double x_m21 = unitM21.Dot(unitx_2); double y_m21 = unitM21.Dot(unity_2); double z_m21 = unitM21.Dot(unitz_2);
	TVector3 M21_Z2frame(y_m21, z_m21, x_m21);
	costheta2 = M21_Z2frame.CosTheta();
	
	// calculate phi
	//calculating phi_n
	TLorentzVector n_p4Z1inXFrame( p4Z1 );
	TLorentzVector n_p4M11inXFrame( p4M11 );
	n_p4Z1inXFrame.Boost( boostX );
	n_p4M11inXFrame.Boost( boostX );        
	TVector3 n_p4Z1inXFrame_unit = n_p4Z1inXFrame.Vect().Unit();
	TVector3 n_p4M11inXFrame_unit = n_p4M11inXFrame.Vect().Unit();  
	TVector3 n_unitz_1( n_p4Z1inXFrame_unit );
	//// y-axis is defined by neg lepton cross z-axis
	//// the subtle part is here...
	//////////TVector3 n_unity_1 = n_p4M11inXFrame_unit.Cross( n_unitz_1 );
	TVector3 n_unity_1 = n_unitz_1.Cross( n_p4M11inXFrame_unit );
	TVector3 n_unitx_1 = n_unity_1.Cross( n_unitz_1 );
	
	TLorentzVector n_p4M21inXFrame( p4M21 );
	n_p4M21inXFrame.Boost( boostX );
	TVector3 n_p4M21inXFrame_unit = n_p4M21inXFrame.Vect().Unit();
	//rotate into other plane
	TVector3 n_p4M21inXFrame_unitprime( n_p4M21inXFrame_unit.Dot(n_unitx_1), n_p4M21inXFrame_unit.Dot(n_unity_1), n_p4M21inXFrame_unit.Dot(n_unitz_1) );
	
	///////-----------------new way of calculating phi-----------------///////
	//double phi_n =  n_p4M21inXFrame_unitprime.Phi();
	/// and then calculate phistar1
	TVector3 n_p4PartoninXFrame_unit( 0.0, 0.0, 1.0 );
	TVector3 n_p4PartoninXFrame_unitprime( n_p4PartoninXFrame_unit.Dot(n_unitx_1), n_p4PartoninXFrame_unit.Dot(n_unity_1), n_p4PartoninXFrame_unit.Dot(n_unitz_1) );
	// negative sign is for arrow convention in paper
	phistar1 = (n_p4PartoninXFrame_unitprime.Phi());
	

}
void calculateAngles(TLorentzVector thep4H, TLorentzVector thep4Z1, TLorentzVector thep4M11, TLorentzVector thep4M12, TLorentzVector thep4Z2, TLorentzVector thep4M21, TLorentzVector thep4M22, double& costheta1, double& costheta2, double& phi, double& costhetastar, double& phistar1, double& phistar2, double& phistar12, double& phi1, double& phi2){
	
	
	//std::cout << "In calculate angles..." << std::endl;
	
	double norm;
	
	TVector3 boostX = -(thep4H.BoostVector());
	TLorentzVector thep4Z1inXFrame( thep4Z1 );
	TLorentzVector thep4Z2inXFrame( thep4Z2 );	
	thep4Z1inXFrame.Boost( boostX );
	thep4Z2inXFrame.Boost( boostX );
	TVector3 theZ1X_p3 = TVector3( thep4Z1inXFrame.X(), thep4Z1inXFrame.Y(), thep4Z1inXFrame.Z() );
	TVector3 theZ2X_p3 = TVector3( thep4Z2inXFrame.X(), thep4Z2inXFrame.Y(), thep4Z2inXFrame.Z() );
	
	// calculate phi1, phi2, costhetastar
	phi1 = theZ1X_p3.Phi();
	phi2 = theZ2X_p3.Phi();
	
	///////////////////////////////////////////////
	// check for z1/z2 convention, redefine all 4 vectors with convention
	///////////////////////////////////////////////	
	TLorentzVector p4H, p4Z1, p4M11, p4M12, p4Z2, p4M21, p4M22;
	p4H = thep4H;

	/* ORDER OF Z1 AND Z2 ALREADY CHOSEN IN MAIN FUNCTION!!!!!! - - - - - - 
	if ((phi1 < 0)&&(phi1 >= -TMath::Pi())){   // old convention based on phi
		p4Z1 = thep4Z2; p4M11 = thep4M21; p4M12 = thep4M22;
		p4Z2 = thep4Z1; p4M21 = thep4M11; p4M22 = thep4M12;		
		costhetastar = theZ2X_p3.CosTheta();
	}
	else{
		p4Z1 = thep4Z1; p4M11 = thep4M11; p4M12 = thep4M12;
		p4Z2 = thep4Z2; p4M21 = thep4M21; p4M22 = thep4M22;
		costhetastar = theZ1X_p3.CosTheta();
	}
	- - - - - - - - - - - - - - - - - - - - - - - - -  - - - - - - - - -*/
	
	p4Z1 = thep4Z1; p4M11 = thep4M11; p4M12 = thep4M12;
	p4Z2 = thep4Z2; p4M21 = thep4M21; p4M22 = thep4M22;
	costhetastar = theZ1X_p3.CosTheta();

	//std::cout << "phi1: " << phi1 << ", phi2: " << phi2 << std::endl;
	
	// now helicity angles................................
	// ...................................................
	TVector3 boostZ1 = -(p4Z1.BoostVector());
	TLorentzVector p4Z2Z1(p4Z2);
	p4Z2Z1.Boost(boostZ1);
	//find the decay axis
	/////TVector3 unitx_1 = -Hep3Vector(p4Z2Z1);
	TVector3 unitx_1( -p4Z2Z1.X(), -p4Z2Z1.Y(), -p4Z2Z1.Z() );
	norm = 1/(unitx_1.Mag());
	unitx_1*=norm;
	//boost daughters of z2
	TLorentzVector p4M21Z1(p4M21);
	TLorentzVector p4M22Z1(p4M22);
	p4M21Z1.Boost(boostZ1);
	p4M22Z1.Boost(boostZ1);
	//create z and y axes
	/////TVector3 unitz_1 = Hep3Vector(p4M21Z1).cross(Hep3Vector(p4M22Z1));
	TVector3 p4M21Z1_p3( p4M21Z1.X(), p4M21Z1.Y(), p4M21Z1.Z() );
	TVector3 p4M22Z1_p3( p4M22Z1.X(), p4M22Z1.Y(), p4M22Z1.Z() );
	TVector3 unitz_1 = p4M21Z1_p3.Cross( p4M22Z1_p3 );
	norm = 1/(unitz_1.Mag());
	unitz_1 *= norm;
	TVector3 unity_1 = unitz_1.Cross(unitx_1);
	
	//caculate theta1
	TLorentzVector p4M11Z1(p4M11);
	p4M11Z1.Boost(boostZ1);
	TVector3 p3M11( p4M11Z1.X(), p4M11Z1.Y(), p4M11Z1.Z() );
	TVector3 unitM11 = p3M11.Unit();
	double x_m11 = unitM11.Dot(unitx_1); double y_m11 = unitM11.Dot(unity_1); double z_m11 = unitM11.Dot(unitz_1);
	TVector3 M11_Z1frame(y_m11, z_m11, x_m11);
	costheta1 = M11_Z1frame.CosTheta();
	//std::cout << "theta1: " << M11_Z1frame.Theta() << std::endl;
	//////-----------------------old way of calculating phi---------------/////////
	phi = M11_Z1frame.Phi();
	
	//set axes for other system
	TVector3 boostZ2 = -(p4Z2.BoostVector());
	TLorentzVector p4Z1Z2(p4Z1);
	p4Z1Z2.Boost(boostZ2);
	TVector3 unitx_2( -p4Z1Z2.X(), -p4Z1Z2.Y(), -p4Z1Z2.Z() );
	norm = 1/(unitx_2.Mag());
	unitx_2*=norm;
	//boost daughters of z2
	TLorentzVector p4M11Z2(p4M11);
	TLorentzVector p4M12Z2(p4M12);
	p4M11Z2.Boost(boostZ2);
	p4M12Z2.Boost(boostZ2);
	TVector3 p4M11Z2_p3( p4M11Z2.X(), p4M11Z2.Y(), p4M11Z2.Z() );
	TVector3 p4M12Z2_p3( p4M12Z2.X(), p4M12Z2.Y(), p4M12Z2.Z() );
	TVector3 unitz_2 = p4M11Z2_p3.Cross( p4M12Z2_p3 );
	norm = 1/(unitz_2.Mag());
	unitz_2*=norm;
	TVector3 unity_2 = unitz_2.Cross(unitx_2);
	//calcuate theta2
	TLorentzVector p4M21Z2(p4M21);
	p4M21Z2.Boost(boostZ2);
	TVector3 p3M21( p4M21Z2.X(), p4M21Z2.Y(), p4M21Z2.Z() );
	TVector3 unitM21 = p3M21.Unit();
	double x_m21 = unitM21.Dot(unitx_2); double y_m21 = unitM21.Dot(unity_2); double z_m21 = unitM21.Dot(unitz_2);
	TVector3 M21_Z2frame(y_m21, z_m21, x_m21);
	costheta2 = M21_Z2frame.CosTheta();
	
	// calculate phi
	//calculating phi_n
	TLorentzVector n_p4Z1inXFrame( p4Z1 );
	TLorentzVector n_p4M11inXFrame( p4M11 );
	n_p4Z1inXFrame.Boost( boostX );
	n_p4M11inXFrame.Boost( boostX );        
	TVector3 n_p4Z1inXFrame_unit = n_p4Z1inXFrame.Vect().Unit();
	TVector3 n_p4M11inXFrame_unit = n_p4M11inXFrame.Vect().Unit();  
	TVector3 n_unitz_1( n_p4Z1inXFrame_unit );
	//// y-axis is defined by neg lepton cross z-axis
	//// the subtle part is here...
	//////////TVector3 n_unity_1 = n_p4M11inXFrame_unit.Cross( n_unitz_1 );
	TVector3 n_unity_1 = n_unitz_1.Cross( n_p4M11inXFrame_unit );
	TVector3 n_unitx_1 = n_unity_1.Cross( n_unitz_1 );
	
	TLorentzVector n_p4M21inXFrame( p4M21 );
	n_p4M21inXFrame.Boost( boostX );
	TVector3 n_p4M21inXFrame_unit = n_p4M21inXFrame.Vect().Unit();
	//rotate into other plane
	TVector3 n_p4M21inXFrame_unitprime( n_p4M21inXFrame_unit.Dot(n_unitx_1), n_p4M21inXFrame_unit.Dot(n_unity_1), n_p4M21inXFrame_unit.Dot(n_unitz_1) );
	
	///////-----------------new way of calculating phi-----------------///////
	//double phi_n =  n_p4M21inXFrame_unitprime.Phi();
	/// and then calculate phistar1
	TVector3 n_p4PartoninXFrame_unit( 0.0, 0.0, 1.0 );
	TVector3 n_p4PartoninXFrame_unitprime( n_p4PartoninXFrame_unit.Dot(n_unitx_1), n_p4PartoninXFrame_unit.Dot(n_unity_1), n_p4PartoninXFrame_unit.Dot(n_unitz_1) );
	// negative sign is for arrow convention in paper
	phistar1 = (n_p4PartoninXFrame_unitprime.Phi());
	
	// and the calculate phistar2
	TLorentzVector n_p4Z2inXFrame( p4Z2 );
	n_p4Z2inXFrame.Boost( boostX );
	TVector3 n_p4Z2inXFrame_unit = n_p4Z2inXFrame.Vect().Unit();
	///////TLorentzVector n_p4M21inXFrame( p4M21 );
	//////n_p4M21inXFrame.Boost( boostX );        
	////TVector3 n_p4M21inXFrame_unit = n_p4M21inXFrame.Vect().Unit();  
	TVector3 n_unitz_2( n_p4Z2inXFrame_unit );
	//// y-axis is defined by neg lepton cross z-axis
	//// the subtle part is here...
	//////TVector3 n_unity_2 = n_p4M21inXFrame_unit.Cross( n_unitz_2 );
	TVector3 n_unity_2 = n_unitz_2.Cross( n_p4M21inXFrame_unit );
	TVector3 n_unitx_2 = n_unity_2.Cross( n_unitz_2 );
	TVector3 n_p4PartoninZ2PlaneFrame_unitprime( n_p4PartoninXFrame_unit.Dot(n_unitx_2), n_p4PartoninXFrame_unit.Dot(n_unity_2), n_p4PartoninXFrame_unit.Dot(n_unitz_2) );
	phistar2 = (n_p4PartoninZ2PlaneFrame_unitprime.Phi());
	
	double phistar12_0 = phistar1 + phistar2;
	if (phistar12_0 > TMath::Pi()) phistar12 = phistar12_0 - 2*TMath::Pi();
	else if (phistar12_0 < (-1.)*TMath::Pi()) phistar12 = phistar12_0 + 2*TMath::Pi();
	else phistar12 = phistar12_0;
	
}
Exemple #17
0
void acceptance(const char* file = "upsilonGun.root", const char* outputName = "acceptance.root") {
  Int_t genUpsSize;
  Float_t genUpsPt[NMAX];
  Float_t genUpsEta[NMAX];
  Float_t genUpsPhi[NMAX];
  Float_t genUpsRapidity[NMAX];
  Int_t genMuSize;
  Float_t genMuPt[NMAX];
  Float_t genMuEta[NMAX];
  Float_t genMuPhi[NMAX];
  Int_t genMuCharge[NMAX];
  Int_t recoMuSize;
  Float_t recoMuPt[NMAX];
  Float_t recoMuEta[NMAX];
  Float_t recoMuPhi[NMAX];
  Int_t recoMuCharge[NMAX];

  TFile* f1 = new TFile(file);
  TTree* t = (TTree*)f1->Get("UpsTree");
  t->SetBranchAddress("genUpsSize",&genUpsSize);
  t->SetBranchAddress("genUpsPt",genUpsPt);
  t->SetBranchAddress("genUpsEta",genUpsEta);
  t->SetBranchAddress("genUpsPhi",genUpsPhi);
  t->SetBranchAddress("genUpsRapidity",genUpsRapidity);
  t->SetBranchAddress("genMuSize",&genMuSize);
  t->SetBranchAddress("genMuPt",genMuPt);
  t->SetBranchAddress("genMuEta",genMuEta);
  t->SetBranchAddress("genMuPhi",genMuPhi);
  t->SetBranchAddress("genMuCharge",genMuCharge);
  t->SetBranchAddress("recoMuSize",&recoMuSize);
  t->SetBranchAddress("recoMuPt",recoMuPt);
  t->SetBranchAddress("recoMuEta",recoMuEta);
  t->SetBranchAddress("recoMuPhi",recoMuPhi);
  t->SetBranchAddress("recoMuCharge",recoMuCharge);

  TH2F* genPtRap = new TH2F("genUps","",4,0,20,4,-2,2);
  TH1F* genPt = new TH1F("genUps1D","",4,0,20);
  genPtRap->Sumw2();
  genPt->Sumw2();
  genPtRap->SetTitle(";Upsilon pT (GeV/c);Upsilon Rapidity;");
  genPt->SetTitle(";Upsilon pT (GeV/c);Acceptance;");
  TH2F* recoPtRap = (TH2F*)genPtRap->Clone("recoUps");
  TH1F* recoPt = (TH1F*)genPt->Clone("recoUps1D");
  recoPtRap->Sumw2();
  recoPt->Sumw2();

  for(int i=0; i<t->GetEntries(); i++){
    if(i%100000 == 0)
      std::cout<<i<<std::endl;
    t->GetEntry(i);

    // calculate cosTheta
    TLorentzVector genUps; genUps.SetPtEtaPhiM(genUpsPt[0], genUpsEta[0], genUpsPhi[0], 9.46);
    TLorentzRotation boost(-genUps.BoostVector());
    int mp = genMuCharge[0]>0 ? 0 : 1;
    TLorentzVector genMuPlus; genMuPlus.SetPtEtaPhiM(genMuPt[mp], genMuEta[mp], genMuPhi[mp], 0.106);
    genMuPlus *= boost;
    Float_t cosThetaStar = genMuPlus.Vect().Dot(genUps.Vect())/genMuPlus.Vect().Mag()/genUps.Vect().Mag();

    // set the weight
    Float_t weight = 1;

    genPtRap->Fill( genUpsPt[0], genUpsRapidity[0], weight );
    genPt->Fill( genUpsPt[0], weight );

    Float_t recoUpsPt = 0;
    Float_t recoUpsRapidity = 0;
    double minDeltaM = 1000;
    for(int tr1=0; tr1<recoMuSize; tr1++){
      for(int tr2=tr1+1; tr2<recoMuSize; tr2++){
        if ( recoMuCharge[tr1]*recoMuCharge[tr2] == -1 && recoMuPt[tr1] >= 3.5 && recoMuPt[tr2] >= 3.5 && fabs(recoMuEta[tr1]) < 2.1 && fabs(recoMuEta[tr2]) < 2.1 ){
          TLorentzVector mu1; mu1.SetPtEtaPhiM(recoMuPt[tr1], recoMuEta[tr1], recoMuPhi[tr1], 0.106);
          TLorentzVector mu2; mu2.SetPtEtaPhiM(recoMuPt[tr2], recoMuEta[tr2], recoMuPhi[tr2], 0.106);
          TLorentzVector recoUps(mu1 + mu2);
          double deltaM = fabs(recoUps.M()-9.46);
          if( deltaM < minDeltaM ){
            recoUpsPt = recoUps.Pt();
            recoUpsRapidity = recoUps.Rapidity();
            minDeltaM = deltaM;
          }
        }
      }
    }
    if( minDeltaM < 1.0 ){
      recoPtRap->Fill( recoUpsPt, recoUpsRapidity, weight );
      recoPt->Fill( recoUpsPt, weight );
    }
  }

  TFile out(outputName,"recreate");
  TH2F* acc = (TH2F*)genPtRap->Clone("acceptance");
  TH1F* acc1D = (TH1F*)genPt->Clone("acceptance1D");
  acc->Sumw2();
  acc1D->Sumw2();
  acc->Divide(recoPtRap,genPtRap,1,1,"B");
  acc1D->Divide(recoPt,genPt,1,1,"B");
  acc->Write();
  acc1D->Write();
  out.Close();
}
Exemple #18
0
void RJ_ttbar(){
  setstyle();
	
  //give transverse momenta to CM system in lab frame?
  double PT = 0.1; //In units of sqrt{shat}
	
  //gamma factor associated with 'off-threshold-ness' of tops
  double gamma = 1.2;
	
  //Now, we also have the option to take gamma, event-by-event, 
  //from a more realistic distribution
  //to do this, set 'b_gamma' to true and the rest
  //of the variables below appropriately
  bool b_gamma = true;
  rootS = 13.;
  type = 1; //0 quark-antiquark  1 gluon-gluon
  M = 175./1000.; //TeV units
	
  //Number of toy events to throw
  int N = 1000;

  //
  // Generate fake events taking flat ME's for all decay angles
  //
	
  //here, we set up the stuff for dynamic gamma
  TH1D *h_gamma = (TH1D*) new TH1D("newgamma","newgamma",500,1.0,10.0);
  if(b_gamma){
    cout << "generating gamma distribution" << endl;
    for(int ibin = 1; ibin <= 500; ibin++){
      double g = h_gamma->GetBinCenter(ibin);
      double entry = Calc_dsigma_dgamma(g);
    
      if(entry > 0.)
	h_gamma->SetBinContent(ibin, entry);
    }
    cout << "done" << endl;
  }
  
  //////////////////////////////////////////////////////////////
  // Setup rest frames code
  //////////////////////////////////////////////////////////////
  cout << " Initialize lists of visible, invisible particles and intermediate states " << endl;
  RLabFrame* LAB = new RLabFrame("LAB","lab");
  RDecayFrame* TT = new RDecayFrame("TT","t #bar{t}");
  RDecayFrame* T1 = new RDecayFrame("T1","t_{a}");
  RDecayFrame* T2 = new RDecayFrame("T2","t_{b}");
  RVisibleFrame* Bjet1 = new RVisibleFrame("B1","b_{a}");
  RVisibleFrame* Bjet2 = new RVisibleFrame("B2","b_{b}");
  RDecayFrame* W1 = new RDecayFrame("W1","W_{a}");
  RDecayFrame* W2 = new RDecayFrame("W2","W_{b}");
  RVisibleFrame* Lep1 = new RVisibleFrame("L1","#it{l}_{a}");
  RVisibleFrame* Lep2 = new RVisibleFrame("L2","#it{l}_{b}");
  RInvisibleFrame* Neu1 = new RInvisibleFrame("NU1","#nu_{a}");
  RInvisibleFrame* Neu2 = new RInvisibleFrame("NU2","#nu_{b}");

  cout << " Define invisible and combinatoric groups " << endl;
  InvisibleGroup INV("INV","Invisible State Jigsaws");
  INV.AddFrame(Neu1);
  INV.AddFrame(Neu2);

  CombinatoricGroup BTAGS("BTAGS","B-tagged jet Jigsaws");
  BTAGS.AddFrame(Bjet1);
  BTAGS.SetNElementsForFrame(Bjet1,1,true);
  BTAGS.AddFrame(Bjet2);
  BTAGS.SetNElementsForFrame(Bjet2,1,true);

  cout << " Build decay tree " << endl;
  LAB->SetChildFrame(TT);

  TT->AddChildFrame(T1);
  TT->AddChildFrame(T2);
  
  T1->AddChildFrame(Bjet1);
  T1->AddChildFrame(W1);
  T2->AddChildFrame(Bjet2);
  T2->AddChildFrame(W2);
  
  W1->AddChildFrame(Lep1);
  W1->AddChildFrame(Neu1);
  W2->AddChildFrame(Lep2);
  W2->AddChildFrame(Neu2);


  //check that tree topology is consistent
  cout << "Is consistent topology: " << LAB->InitializeTree() << endl; 

  cout << "Initializing jigsaw rules" << endl; 

  InvisibleMassJigsaw MinMassJigsaw("MINMASS_JIGSAW", "Invisible system mass Jigsaw");
  INV.AddJigsaw(MinMassJigsaw);

  InvisibleRapidityJigsaw RapidityJigsaw("RAPIDITY_JIGSAW", "Invisible system rapidity Jigsaw");
  INV.AddJigsaw(RapidityJigsaw);
  RapidityJigsaw.AddVisibleFrame((LAB->GetListVisibleFrames()));
  
  
  ContraBoostInvariantJigsaw TopJigsaw("TOP_JIGSAW","Contraboost invariant Jigsaw");
  INV.AddJigsaw(TopJigsaw);
  TopJigsaw.AddVisibleFrame((T1->GetListVisibleFrames()), 0);
  TopJigsaw.AddVisibleFrame((T2->GetListVisibleFrames()), 1);
  TopJigsaw.AddInvisibleFrame((T1->GetListInvisibleFrames()), 0);
  TopJigsaw.AddInvisibleFrame((T2->GetListInvisibleFrames()), 1);

  MinimizeMassesCombinatoricJigsaw BLJigsaw("BL_JIGSAW","Minimize m_{b#it{l}}'s Jigsaw");
  BTAGS.AddJigsaw(BLJigsaw);
  BLJigsaw.AddFrame(Bjet1,0);
  BLJigsaw.AddFrame(Lep1,0);
  BLJigsaw.AddFrame(Bjet2,1);
  BLJigsaw.AddFrame(Lep2,1);

  cout << "Initializing the tree for analysis : " << LAB->InitializeAnalysis() << endl; 

  //draw tree with jigsaws
  FramePlot* jigsaw_plot = new FramePlot("tree","Decay Tree");
  jigsaw_plot->AddFrameTree(LAB);
  jigsaw_plot->AddJigsaw(TopJigsaw);
  jigsaw_plot->AddJigsaw(BLJigsaw);
  jigsaw_plot->DrawFramePlot();
	
  for(int i = 0; i < N; i++){
    if(b_gamma){
      gamma = h_gamma->GetRandom();
    }
   	
    //////////////////////////////////////////////////////////////
    // BEGIN CODE TO generate toy GEN LEVEL events
    //////////////////////////////////////////////////////////////
    double Mt1 = 175.;
    double MW1 = 80.;
    double Mt2 = 175.;
    double MW2 = 80.;
		
    double Mnu1 = 0.;
    double Mnu2 = 0.;
		
    GetLepTopHem(0, Mt1, MW1, 5., 0.005, Mnu1);
    GetLepTopHem(1, Mt2, MW2, 5., 0.005, Mnu2);
		
    double EB1 = (Mt1*Mt1 - MW1*MW1)/(2.*Mt1);
    double EB2 = (Mt2*Mt2 - MW2*MW2)/(2.*Mt2);
		
    double EVIS1 = (Mt1*Mt1 - Mnu1*Mnu1)/(Mt1);
    double EVIS2 = (Mt2*Mt2 - Mnu2*Mnu2)/(Mt2);
		
    double EW1 = (Mt1*Mt1 + MW1*MW1)/(2.*Mt1);
    double EW2 = (Mt2*Mt2 + MW2*MW2)/(2.*Mt2);
		
    double EL1 = (MW1*MW1-Mnu1*Mnu1)/(2.*MW1);
    double EL2 = (MW2*MW2-Mnu2*Mnu2)/(2.*MW2);
		
    double gamma1 = EW1/MW1;
    double gamma2 = EW2/MW2;
    double beta1 = 1.;
    double beta2 = 1.;
		
    //put them in the lab frame
    BoostToLabFrame(gamma);
		
    // effective gamma factor for parents in CM frame
    double g_eff = (P[0]+P[1]).M()/(2.*sqrt(P[0].M()*P[1].M()));
		
    PtBoost(PT);
    //////////////////////////////////////////////////////////////
    // END CODE TO generate toy GEN LEVEL event
    //////////////////////////////////////////////////////////////
        
    //////////////////////////////////////////////////////////////
    // BEGIN CODE TO analyze GEN LEVEL events
    //////////////////////////////////////////////////////////////
    
    //////////////////////////////////////////////////////////////
    // First, we calculate approximate neutrino 4-vectors
    // in W frames using two different strategies
    //////////////////////////////////////////////////////////////
        
    TLorentzVector NU1_top, NU2_top, NU1_W, NU2_W;
      
    //
    // first, we will assign 4-vectos in the lab frame for
    // NU1_top and NU2_top by drawing a contraboost invariant symmetry 
    // between the two BL systems and neutrinos. 
    // Here, the tops are assumed to have the same boost factor in TT 
    // rest frame.
    //
    for(;;){
      // get MET in lab frame 
      TVector3 MET = (vMiss[0]+vMiss[1]).Vect();
      MET.SetZ(0.0);
      // get b-quarks in lab frame
      TLorentzVector B1, B2;
      B1 = C_2[0];
      B2 = C_2[1];
      // get leptons in lab frame
      TLorentzVector L1, L2;
      L1 = C_1_1[0];
      L2 = C_1_1[1];
      //
      // We separate the objects into decay hemispheres
      // practice we will need to assign BL pairs according to
      // metric (see commented below)
      //
      
      TLorentzVector VISTOT = B1+L1+B2+L2;
      TVector3 boostTOT = VISTOT.BoostVector();
      B1.Boost(-boostTOT);
      B2.Boost(-boostTOT);
      L1.Boost(-boostTOT);
      L2.Boost(-boostTOT);
      if( (B1+L2).P() > (B1+L1).P() ){
	TLorentzVector temp = B1;
	B1 = B2;
	B2 = temp;
      }
      B1.Boost(boostTOT);
      B2.Boost(boostTOT);
      L1.Boost(boostTOT);
      L2.Boost(boostTOT);

      //
      // visible hemispheres of top decays
      //
      TLorentzVector H1 = (B1+L1);
      TLorentzVector H2 = (B2+L2);

      //
      // We will now attempt to travel through approximations of each of the rest frames 
      // of interest, beginning in the lab frame and ending in the TT rest frame, where
      // we will specify the neutrino 4-momenta according to a contraboost invariant 
      // symmetry between the visible and invisible decay products of the two tops
      //
      
      //
      // first, we boost from the lab frame to intermediate 'CMz' frame
      // i.e. with the visible hemispheres' vectoral sum zero
      //
      TVector3 BL = H1.Vect()+H2.Vect();
      BL.SetX(0.0);
      BL.SetY(0.0);
      BL = (1./(H1.E()+H2.E()))*BL;
		
      B1.Boost(-BL);
      L1.Boost(-BL);
      B2.Boost(-BL);
      L2.Boost(-BL);
      H1.Boost(-BL);
      H2.Boost(-BL);
		 
      //
      // Now, we need to 'guess' the invariant mass of the weakly interacting system
      // as a Lorentz-invariant quantity which is a function of the visible system
      // masses, and large enough to accomodate the contraboost invariant 
      // solution we will use in the following TT CM frame. This allows us to write down
      // the transverse part of the boost from lab to TT CM frame.
      //
      
      double Minv2 = (H1+H2).M2() - 4.*H1.M()*H2.M();
      //double Minv2 = (H1+H2).M2() - 4.*min(H1.M2(),H2.M2());

      //
      // transverse momentum of total TT system in lab frame
      // NOTE: (H1+H2).Pz() == 0 due to previous longitudinal boost
      //
      TVector3 PT = MET+(H1+H2).Vect();
      double Einv2 = MET.Mag2() + Minv2;
      PT.SetZ(0.0); // redundant
      //
      // transverse boost from 'CMz' frame to TT CM frame
      //
      TVector3 BT = (1./( (H1+H2).E() + sqrt(Einv2) ))*PT;
      B1.Boost(-BT);
      L1.Boost(-BT);
      B2.Boost(-BT);
      L2.Boost(-BT);
      H1.Boost(-BT);
      H2.Boost(-BT);
      
      //
      // Now, in TT CM approx frame we will make a contraboost invariant choise for the assymmetric boost, then specifying 
      // neutrino 4-vectors
      // 
      //
      // contra-boost invariant quantities (for this boost)
      //
      double m1 = H1.M();
      double m2 = H2.M();
      double MC2 = 2.*( H1.E()*H2.E() + H1.Vect().Dot(H2.Vect()) );
     
      //
      // contra-boost invariant coefficients
      //
      double k1 = m1*m1-m2*m2 + MC2 - 2.*m1*m2;
      double k2 = m2*m2-m1*m1 + MC2 - 2.*m1*m2;

      double N = ( fabs(k1*m1*m1 - k2*m2*m2) - 0.5*fabs(k2-k1)*MC2 + 0.5*(k1+k2)*sqrt(MC2*MC2-4.*m1*m1*m2*m2) )/(k1*k1*m1*m1+k2*k2*m2*m2+k1*k2*MC2);

      double c1 = 0.5*(1.+N*k1);
      double c2 = 0.5*(1.+N*k2);

      //c1 = 1;
      //c2 = 1;
		
      // 
      // adjust coefficients such that di-neutrino invariant mass is equal to the Lorentz-invariant value we chose earlier,
      // maintaining a contra-boost invariant ratio
      //
      double A = ( H1.E()+H2.E() + sqrt( (H1.E()+H2.E())*(H1.E()+H2.E()) -(H1+H2).M2() + Minv2 ))/(c1*H1.E()+c2*H2.E())/2.;

      c1 *= A;
      c2 *= A;
                
      double Enu1 = (c1-1.)*H1.E() + c2*H2.E();
      double Enu2 = c1*H1.E() + (c2-1.)*H2.E();
      TVector3 pnu1 = (c1-1.)*H1.Vect() - c2*H2.Vect();
      TVector3 pnu2 = (c2-1.)*H2.Vect() - c1*H1.Vect();

      //
      // define neutrino 4-vectors
      //
      NU1_top.SetPxPyPzE(pnu1.X(),pnu1.Y(),pnu1.Z(),Enu1);
      NU2_top.SetPxPyPzE(pnu2.X(),pnu2.Y(),pnu2.Z(),Enu2);

      //
      // now, transform neutrinos back into lab frame
      //
      NU1_top.Boost(BT);
      NU2_top.Boost(BT);
      NU1_top.Boost(BL);
      NU2_top.Boost(BL);
            
      break;
    }
		
    //
    // Next, we will assign 4-vectos in the lab frame for
    // NU1_W and NU2_W by drawing a contraboost invariant symmetry 
    // between the two L systems and neutrinos. 
    // Here, the W's are assumed to have the same boost factor in the WW  
    // rest frame.
    //
    for(;;){
      TVector3 MET = (vMiss[0]+vMiss[1]).Vect();
      MET.SetZ(0.0);
      //get b-quarks in lab frame
      TLorentzVector B1, B2;
      B1 = C_2[0];
      B2 = C_2[1];
      //get leptons in lab frame
      TLorentzVector L1, L2;
      L1 = C_1_1[0];
      L2 = C_1_1[1];
      //
      // We separate the objects into decay hemispheres
      // practice we will need to assign BL pairs according to
      // metric (see commented below)
      //
      TLorentzVector VISTOT = B1+L1+B2+L2;
      TVector3 boostTOT = VISTOT.BoostVector();
      B1.Boost(-boostTOT);
      B2.Boost(-boostTOT);
      L1.Boost(-boostTOT);
      L2.Boost(-boostTOT);
      if( (B1+L2).P() > (B1+L1).P() ){
	TLorentzVector temp = B1;
	B1 = B2;
	B2 = temp;
      }
      B1.Boost(boostTOT);
      B2.Boost(boostTOT);
      L1.Boost(boostTOT);
      L2.Boost(boostTOT);
      //
      // visible hemispheres of top decays
      //
      TLorentzVector H1 = (B1+L1);
      TLorentzVector H2 = (B2+L2);
            
      //
      // We will now attempt to travel through approximations of each of the rest frames 
      // of interest, beginning in the lab frame and ending in the WW rest frame, where
      // we will specify the neutrino 4-momenta according to a contraboost invariant 
      // symmetry between the visible and invisible decay products of the two W's
      //
      
      //
      // first, we boost from the lab frame to intermediate 'CMz' frame
      // i.e. with the visible hemispheres' vectoral sum zero
      //
      TVector3 BL = H1.Vect()+H2.Vect();
      BL.SetX(0.0);
      BL.SetY(0.0);
      BL = (1./(H1.E()+H2.E()))*BL;
            
      B1.Boost(-BL);
      L1.Boost(-BL);
      B2.Boost(-BL);
      L2.Boost(-BL);
      H1.Boost(-BL);
      H2.Boost(-BL);
            
      //
      // Now, we need to 'guess' the invariant mass of the weakly interacting system
      // as a Lorentz-invariant quantity which is a function of the visible system
      // masses, and large enough to accomodate the contraboost invariant 
      // solution we will use in the following WW CM frame. This allows us to write down
      // the transverse part of the boost from lab to WW CM frame.
      //
      double Minv2 = (L1+L2).M2();
      TVector3 PT = MET+(L1+L2).Vect();
      double Einv2 = MET.Mag2() + Minv2;
     
      TVector3 BT = (1./( (L1+L2).E() + sqrt(Einv2) ))*PT;
      L1.Boost(-BT);
      L2.Boost(-BT);
      //
      // Now, in WW CM approx frame we will make a contraboost invariant choise for the assymmetric boost, then specifying 
      // neutrino 4-vectors
      // 
      //
      // contra-boost invariant coefficients are both 1, scaling factor to fix di-neutrino invariant mass
      // is 1, since (L1+L2).M2() = Minv2
      //
      double c = ( L1.E()+L2.E() + sqrt( (L1.E()+L2.E())*(L1.E()+L2.E()) -(L1+L2).M2() + Minv2 ))/(L1.E()+L2.E())/2.; //obviously redundant
            
      double Enu1 = (c-1.)*L1.E() + c*L2.E();
      double Enu2 = c*L1.E() + (c-1.)*L2.E();
      TVector3 pnu1 = (c-1.)*L1.Vect() - c*L2.Vect();
      TVector3 pnu2 = (c-1.)*L2.Vect() - c*L1.Vect();
            
      //define neutrino 4-vectors
      NU1_W.SetPxPyPzE(pnu1.X(),pnu1.Y(),pnu1.Z(),Enu1);
      NU2_W.SetPxPyPzE(pnu2.X(),pnu2.Y(),pnu2.Z(),Enu2);
            
      //now, go back to lab frame
      NU1_W.Boost(BT);
      NU2_W.Boost(BT);
      NU1_W.Boost(BL);
      NU2_W.Boost(BL);
            
      break;
    }
    //
    // Now we have our guess for the neutrino 4-vectors in the lab frame
    // using two different approaches (top or W symmetry, NUi_top and NUi_W
    // 4-vectors, respectively), along with the 'truth' values.
    // We will now go through all of the relevant reference frames in our approximate 
    // reconstructions and in truth simultaenously to calculate observables
    //
    TLorentzVector B1, B2;
    B1 = C_2[0];
    B2 = C_2[1];
    //get leptons in lab frame
    TLorentzVector L1, L2;
    L1 = C_1_1[0];
    L2 = C_1_1[1];
    //get truth neutrinos in lab frame
    TLorentzVector NU1, NU2;
    NU1 = C_1_2[0];
    NU2 = C_1_2[1];

    TVector3 MET = (vMiss[0]+vMiss[1]).Vect();
    MET.SetZ(0.0);

    INV.ClearEvent();
    BTAGS.ClearEvent();

    Lep1->SetLabFrameFourVector(L1);
    Lep2->SetLabFrameFourVector(L2);
    GroupElementID B1_ID = BTAGS.AddLabFrameFourVector(B1);
    GroupElementID B2_ID = BTAGS.AddLabFrameFourVector(B2);
    INV.SetLabFrameThreeVector(MET);

    LAB->AnalyzeEvent();

    //
    // Now we have two different sets of neutrino guesses in lab frame - define matching visible particles
    //
    TLorentzVector B1_top = B1;
    TLorentzVector B2_top = B2;
    TLorentzVector L1_top = L1;
    TLorentzVector L2_top = L2;
    TLorentzVector B1_W = B1;
    TLorentzVector B2_W = B2;
    TLorentzVector L1_W = L1;
    TLorentzVector L2_W = L2;
    //
    // We separate the objects into decay hemispheres
    // practice we will need to assign BL pairs according to
    // metric for 'reconstructed' events (see commented below)
    //
    
      TLorentzVector VISTOT_top = B1_top+L1_top+B2_top+L2_top;
      TVector3 boostTOT_top = VISTOT_top.BoostVector();
      B1_top.Boost(-boostTOT_top);
      B2_top.Boost(-boostTOT_top);
      L1_top.Boost(-boostTOT_top);
      L2_top.Boost(-boostTOT_top);
      if( (B1_top+L2_top).P() > (B1_top+L1_top).P() ){
	TLorentzVector temp = B1_top;
	B1_top = B2_top;
	B2_top = temp;
      }
      B1_top.Boost(boostTOT_top);
      B2_top.Boost(boostTOT_top);
      L1_top.Boost(boostTOT_top);
      L2_top.Boost(boostTOT_top);

      /*
      if( (B1_W+L1_W).M2()+(B2_W+L2_W).M2() > (B1_W+L2_W).M2()+(B2_W+L1_W).M2() ){
	TLorentzVector temp = L1_W;
	L1_W = L2_W;
	L2_W = temp;
      }
    */
    //
    // visible hemispheres of top decays
    //
    TLorentzVector H1 = L1+B1+NU1;
    TLorentzVector H2 = L2+B2+NU2;
    TLorentzVector H1_top = L1_top+B1_top+NU1_top;
    TLorentzVector H2_top = L2_top+B2_top+NU2_top;
    TLorentzVector H1_W = L1+B1+NU1_W;
    TLorentzVector H2_W = L2+B2+NU2_W;
    
    
    cout << "TT mass: " << (H1_top+H2_top).M() << " " << TT->GetMass() << endl;
    cout << "T1 mass: " << H1_top.M() << " " << T1->GetMass() << endl;
    cout << "T2 mass: " << H2_top.M() << " " << T2->GetMass() << endl;
    cout << "W1 mass: " << (L1_top+NU1_top).M() << " " << W1->GetMass() << endl;
    cout << "W2 mass: " << (L2_top+NU2_top).M() << " " << W2->GetMass() << endl;
    cout << "NU1 mass: " << NU1_top.M() << " " << Neu1->GetMass() << endl;
    cout << "NU2 mass: " << NU2_top.M() << " " << Neu2->GetMass() << endl;
    cout << "MET: " << (Neu1->GetFourVector(LAB)+Neu2->GetFourVector(LAB)).Pt() << " " << MET.Mag() << endl;
    
    /*
    cout << "TT mass: " << (H1_W+H2_W).M() << " " << TT->GetMass() << endl;
    cout << "T1 mass: " << H1_W.M() << " " << T1->GetMass() << endl;
    cout << "T2 mass: " << H2_W.M() << " " << T2->GetMass() << endl;
    cout << "W1 mass: " << (L1+NU1_W).M() << " " << W1->GetMass() << endl;
    cout << "W2 mass: " << (L2+NU2_W).M() << " " << W2->GetMass() << endl;
    cout << "NU1 mass: " << NU1_W.M() << " " << Neu1->GetMass() << endl;
    cout << "NU2 mass: " << NU2_W.M() << " " << Neu2->GetMass() << endl;
    */
    //
    // In the lab frame - let's move now to the ttbar CM frame
    // boosts
    //
    TVector3 BltoCM = (H1+H2).BoostVector();
    TVector3 BltoCM_top = (H1_top+H2_top).BoostVector();
    TVector3 BltoCM_W = (H1_W+H2_W).BoostVector();

    H1.Boost(-BltoCM);
    H2.Boost(-BltoCM);
    L1.Boost(-BltoCM);
    L2.Boost(-BltoCM);
    NU1.Boost(-BltoCM);
    NU2.Boost(-BltoCM);
    B1.Boost(-BltoCM);
    B2.Boost(-BltoCM);
    H1_top.Boost(-BltoCM_top);
    H2_top.Boost(-BltoCM_top);
    L1_top.Boost(-BltoCM_top);
    L2_top.Boost(-BltoCM_top);
    B1_top.Boost(-BltoCM_top);
    B2_top.Boost(-BltoCM_top);
    NU1_top.Boost(-BltoCM_top);
    NU2_top.Boost(-BltoCM_top);
    H1_W.Boost(-BltoCM_W);
    H2_W.Boost(-BltoCM_W);
    L1_W.Boost(-BltoCM_W);
    L2_W.Boost(-BltoCM_W);
    B1_W.Boost(-BltoCM_W);
    B2_W.Boost(-BltoCM_W);
    NU1_W.Boost(-BltoCM_W);
    NU2_W.Boost(-BltoCM_W);

    //
    // angles in the TT CM frames, approximate and true
    //
    double costhetaTT = H1.Vect().Unit().Dot( BltoCM.Unit() );
    double dphiTT = fabs(H1.Vect().DeltaPhi( BltoCM ));
    double dphiM  = fabs( (B1+B2+L1+L2).Vect().DeltaPhi( BltoCM ));
    double costhetaTT_top = fabs( H1_top.Vect().Unit().Dot( BltoCM_top.Unit() ));
    double dphiTT_top = fabs(H1_top.Vect().DeltaPhi( BltoCM_top ));
    double dphiM_top  = fabs( (B1_top+B2_top+L1_top+L2_top).Vect().DeltaPhi( BltoCM_top ));
    double costhetaTT_W = fabs( H1_W.Vect().Unit().Dot( BltoCM_W.Unit() ));
    double dphiTT_W = fabs(H1_W.Vect().DeltaPhi( BltoCM_W ));
    double dphiM_W  = fabs( (B1_W+B2_W+L1_W+L2_W).Vect().DeltaPhi( BltoCM_W ));
    //scale
    double MTT = (H1+H2).M();
    double MTT_top = (H1_top+H2_top).M();
    double MTT_W = (H1_W+H2_W).M();
    
    // vector normal to decay plane of CM frame (for later azimuthal angles)
    TVector3 vNORM_CM_T1 = B1.Vect().Cross((L1+NU1).Vect());
    TVector3 vNORM_CM_T2 = B2.Vect().Cross((L2+NU2).Vect());
    double dphi_T1_T2 = vNORM_CM_T1.Angle(vNORM_CM_T2);
    double dot_dphi_T1_T2 = B1.Vect().Dot(vNORM_CM_T2);
    if(dot_dphi_T1_T2 < 0.0 && dphi_T1_T2 > 0.0){
      dphi_T1_T2 = TMath::Pi()*2. - dphi_T1_T2;
    }
    TVector3 vNORM_CM_T1_top = B1_top.Vect().Cross((L1_top+NU1_top).Vect());
    TVector3 vNORM_CM_T2_top = B2_top.Vect().Cross((L2_top+NU2_top).Vect());
    double dphi_T1_T2_top = vNORM_CM_T1_top.Angle(vNORM_CM_T2_top);
    double dot_dphi_T1_T2_top = B1_top.Vect().Dot(vNORM_CM_T2_top);
    if(dot_dphi_T1_T2_top < 0.0 && dphi_T1_T2_top > 0.0){
      dphi_T1_T2_top = TMath::Pi()*2. - dphi_T1_T2_top;
    }
    TVector3 vNORM_CM_T1_W = B1_W.Vect().Cross((L1_W+NU1_W).Vect());
    TVector3 vNORM_CM_T2_W = B2_W.Vect().Cross((L2_W+NU2_W).Vect());
    double dphi_T1_T2_W = vNORM_CM_T1_W.Angle(vNORM_CM_T2_W);
    double dot_dphi_T1_T2_W = B1.Vect().Dot(vNORM_CM_T2_W);
    if(dot_dphi_T1_T2_W < 0.0 && dphi_T1_T2_W > 0.0){
      dphi_T1_T2_W = TMath::Pi()*2. - dphi_T1_T2_W;
    }
    
    double ddphi_T1_T2_top = sin(dphi_T1_T2_top-dphi_T1_T2);
    double ddphi_T1_T2_W = sin(dphi_T1_T2_W-dphi_T1_T2);

    //
    // To the next frames!!!!
    // now, to 'top' CM frame approxs and truth
    //
    TVector3 BCMtoT1 = H1.BoostVector();
    TVector3 BCMtoT2 = H2.BoostVector();
    TVector3 BCMtoT1_top = H1_top.BoostVector();
    TVector3 BCMtoT2_top = H2_top.BoostVector();
    TVector3 BCMtoT1_W = H1_W.BoostVector();
    TVector3 BCMtoT2_W = H2_W.BoostVector();

    B1.Boost(-BCMtoT1);
    B2.Boost(-BCMtoT2);
    L1.Boost(-BCMtoT1);
    L2.Boost(-BCMtoT2);
    NU1.Boost(-BCMtoT1);
    NU2.Boost(-BCMtoT2);
    B1_top.Boost(-BCMtoT1_top);
    B2_top.Boost(-BCMtoT2_top);
    L1_top.Boost(-BCMtoT1_top);
    L2_top.Boost(-BCMtoT2_top);
    NU1_top.Boost(-BCMtoT1_top);
    NU2_top.Boost(-BCMtoT2_top);
    B1_W.Boost(-BCMtoT1_W);
    B2_W.Boost(-BCMtoT2_W);
    L1_W.Boost(-BCMtoT1_W);
    L2_W.Boost(-BCMtoT2_W);
    NU1_W.Boost(-BCMtoT1_W);
    NU2_W.Boost(-BCMtoT2_W);

    cout <<  W1->GetFourVector(T1).E() << " " << (L1_top+NU1_top).E() << endl;
    cout <<  W2->GetFourVector(T2).E() << " " << (L2_top+NU2_top).E() << endl;

    //
    // decay angles in top frames
    //
    double costhetaT1 = B1.Vect().Unit().Dot(BCMtoT1.Unit());
    double costhetaT2 = B2.Vect().Unit().Dot(BCMtoT2.Unit());
    double costhetaT1_top = B1_top.Vect().Unit().Dot(BCMtoT1_top.Unit());
    double costhetaT2_top = B2_top.Vect().Unit().Dot(BCMtoT2_top.Unit());
    double costhetaT1_W = B1_W.Vect().Unit().Dot(BCMtoT1_W.Unit());
    double costhetaT2_W = B2_W.Vect().Unit().Dot(BCMtoT2_W.Unit());
    double dcosthetaT1_top = costhetaT1_top*sqrt(1.-costhetaT1*costhetaT1)-costhetaT1*sqrt(1.-costhetaT1_top*costhetaT1_top);
    double dcosthetaT2_top = costhetaT2_top*sqrt(1.-costhetaT2*costhetaT2)-costhetaT2*sqrt(1.-costhetaT2_top*costhetaT2_top);
    double dcosthetaT1_W = costhetaT1_W*sqrt(1.-costhetaT1*costhetaT1)-costhetaT1*sqrt(1.-costhetaT1_W*costhetaT1_W);
    double dcosthetaT2_W = costhetaT2_W*sqrt(1.-costhetaT2*costhetaT2)-costhetaT2*sqrt(1.-costhetaT2_W*costhetaT2_W);

    //vectors normal to decay planes of T frames
    TVector3 vNORM_T1_B = B1.Vect().Cross(BCMtoT1);
    TVector3 vNORM_T2_B = B2.Vect().Cross(BCMtoT2);
    TVector3 vNORM_T1_B_top = B1_top.Vect().Cross(BCMtoT1_top);
    TVector3 vNORM_T2_B_top = B2_top.Vect().Cross(BCMtoT2_top);
    TVector3 vNORM_T1_B_W = B1_W.Vect().Cross(BCMtoT1_W);
    TVector3 vNORM_T2_B_W = B2_W.Vect().Cross(BCMtoT2_W);
    //vectors normal to W decay planes in T frames
    TVector3 vNORM_T1_W = L1.Vect().Cross(NU1.Vect());
    TVector3 vNORM_T2_W = L2.Vect().Cross(NU2.Vect());
    TVector3 vNORM_T1_W_top = L1_top.Vect().Cross(NU1_top.Vect());
    TVector3 vNORM_T2_W_top = L2_top.Vect().Cross(NU2_top.Vect());
    TVector3 vNORM_T1_W_W = L1_W.Vect().Cross(NU1_W.Vect());
    TVector3 vNORM_T2_W_W = L2_W.Vect().Cross(NU2_W.Vect());

    double dphi_W_T1 = vNORM_T1_W.Angle(vNORM_T1_B);
    double dphi_W_T2 = vNORM_T2_W.Angle(vNORM_T2_B);
    double dot_dphi_W_T1 = L1.Vect().Dot(vNORM_T1_B);
    double dot_dphi_W_T2 = L2.Vect().Dot(vNORM_T2_B);
    if(dot_dphi_W_T1 < 0.0 && dphi_W_T1 > 0.0){
      dphi_W_T1 = TMath::Pi()*2. - dphi_W_T1;
    }
    if(dot_dphi_W_T2 < 0.0 && dphi_W_T2 > 0.0){
      dphi_W_T2 = TMath::Pi()*2. - dphi_W_T2;
    }
    double dphi_W_T1_top = vNORM_T1_W_top.Angle(vNORM_T1_B_top);
    double dphi_W_T2_top = vNORM_T2_W_top.Angle(vNORM_T2_B_top);
    double dot_dphi_W_T1_top = L1_top.Vect().Dot(vNORM_T1_B_top);
    double dot_dphi_W_T2_top = L2_top.Vect().Dot(vNORM_T2_B_top);
    if(dot_dphi_W_T1_top < 0.0 && dphi_W_T1_top > 0.0){
      dphi_W_T1_top = TMath::Pi()*2. - dphi_W_T1_top;
    }
    if(dot_dphi_W_T2_top < 0.0 && dphi_W_T2_top > 0.0){
      dphi_W_T2_top = TMath::Pi()*2. - dphi_W_T2_top;
    }
    double dphi_W_T1_W = vNORM_T1_W_W.Angle(vNORM_T1_B_W);
    double dphi_W_T2_W = vNORM_T2_W_W.Angle(vNORM_T2_B_W);
    double dot_dphi_W_T1_W = L1_W.Vect().Dot(vNORM_T1_B_W);
    double dot_dphi_W_T2_W = L2_W.Vect().Dot(vNORM_T2_B_W);
    if(dot_dphi_W_T1_W < 0.0 && dphi_W_T1_W > 0.0){
      dphi_W_T1_W = TMath::Pi()*2. - dphi_W_T1_W;
    }
    if(dot_dphi_W_T2_W < 0.0 && dphi_W_T2_W > 0.0){
      dphi_W_T2_W = TMath::Pi()*2. - dphi_W_T2_W;
    }

    //
    // differences between true and reco azimuthal angles
    //
    double ddphi_W_T1_top = sin(dphi_W_T1_top-dphi_W_T1);
    double ddphi_W_T2_top = sin(dphi_W_T2_top-dphi_W_T2);
    double ddphi_W_T1_W = sin(dphi_W_T1_W-dphi_W_T1);
    double ddphi_W_T2_W = sin(dphi_W_T2_W-dphi_W_T2);
    
    //
    // gamma for asymmetric boost
    //
    double gammaT = 1./pow( (1.-BCMtoT1.Mag2())*(1.-BCMtoT2.Mag2()),1./4. );
    double gammaT_top = 1./sqrt(1.-BCMtoT1_top.Mag2());
    double gammaT_W = 1./pow( (1.-BCMtoT1_W.Mag2())*(1.-BCMtoT2_W.Mag2()),1./4. );
    //
    // scale variables
    //
    double MT1 = H1.M();
    double MT2 = H2.M();
    double MT_top = H1_top.M();
    double MT1_W = H1_W.M();
    double MT2_W = H2_W.M();
  
    double Eb1 = B1.E();
    double Eb2 = B2.E();
    double Eb1_top = B1_top.E();
    double Eb2_top = B2_top.E();
    double Eb1_W = B1_W.E();
    double Eb2_W = B2_W.E();

    //
    // Heading to the last frames!!!!!
    // from the T rest frames to the W rest frames
    //
    TVector3 BTtoW1 = (L1+NU1).BoostVector();
    TVector3 BTtoW2 = (L2+NU2).BoostVector();
    TVector3 BTtoW1_top = (L1_top+NU1_top).BoostVector();
    TVector3 BTtoW2_top = (L2_top+NU2_top).BoostVector();
    TVector3 BTtoW1_W = (L1_W+NU1_W).BoostVector();
    TVector3 BTtoW2_W = (L2_W+NU2_W).BoostVector();

    L1.Boost(-BTtoW1);
    NU1.Boost(-BTtoW1);
    L2.Boost(-BTtoW2);
    NU2.Boost(-BTtoW2);
    L1_top.Boost(-BTtoW1_top);
    NU1_top.Boost(-BTtoW1_top);
    L2_top.Boost(-BTtoW2_top);
    NU2_top.Boost(-BTtoW2_top);
    L1_W.Boost(-BTtoW1_W);
    NU1_W.Boost(-BTtoW1_W);
    L2_W.Boost(-BTtoW2_W);
    NU2_W.Boost(-BTtoW2_W);

    //
    // scales in the W rest frame
    //
    double El1 = L1.E();
    double El2 = L2.E();
    double El1_top = L1_top.E();
    double El2_top = L2_top.E();
    double El1_W = L1_W.E();
    double El2_W = L2_W.E();
    
    //calculate some angles
    double costhetaW1 = L1.Vect().Unit().Dot(BTtoW1.Unit());
    double costhetaW2 = L2.Vect().Unit().Dot(BTtoW2.Unit());
    double costhetaW1_top = L1_top.Vect().Unit().Dot(BTtoW1_top.Unit());
    double costhetaW2_top = L2_top.Vect().Unit().Dot(BTtoW2_top.Unit());
    double costhetaW1_W = L1_W.Vect().Unit().Dot(BTtoW1_W.Unit());
    double costhetaW2_W = L2_W.Vect().Unit().Dot(BTtoW2_W.Unit());
    double dcosthetaW1_top = costhetaW1*sqrt(1.-costhetaW1_top*costhetaW1_top) - costhetaW1_top*sqrt(1.-costhetaW1*costhetaW1);
    double dcosthetaW2_top = costhetaW2*sqrt(1.-costhetaW2_top*costhetaW2_top) - costhetaW2_top*sqrt(1.-costhetaW2*costhetaW2);
    double dcosthetaW1_W = costhetaW1*sqrt(1.-costhetaW1_W*costhetaW1_W) - costhetaW1_W*sqrt(1.-costhetaW1*costhetaW1);
    double dcosthetaW2_W = costhetaW2*sqrt(1.-costhetaW2_W*costhetaW2_W) - costhetaW2_W*sqrt(1.-costhetaW2*costhetaW2);

    // define different scale sensitive ratios
    double El1Eb1_top = El1_top/(El1_top+Eb1_top);
    double El1Eb1_W = El1_W/(El1_W+Eb1_W);
    double El1Eb2_top = El1_top/(El1_top+Eb2_top);
    double El1Eb2_W = El1_W/(El1_W+Eb2_W);

    
    cout << "TT costheta: " << costhetaTT_top << " " << TT->GetCosDecayAngle() << endl;
    cout << "T1 costheta: " << costhetaT1_top << " " << T1->GetCosDecayAngle() << endl;
    cout << "T2 costheta: " << costhetaT2_top << " " << T2->GetCosDecayAngle() << endl;
    cout << "dphi_T1_T2_top: " << dphi_T1_T2_top << " " << T1->GetDeltaPhiDecayPlanes(T2) << endl;
    cout << "dphi_W_T1_top: " << dphi_W_T1_top << " " << T1->GetDeltaPhiDecayPlanes(W1) << endl;
   
    
    TLorentzVector newB1 = Bjet1->GetFourVector(T1);
    TLorentzVector newB2 = Bjet2->GetFourVector(T2);
    TLorentzVector newL1 = Lep1->GetFourVector(W1);
    TLorentzVector newL2 = Lep2->GetFourVector(W2);
    TLorentzVector newNU1 = Neu1->GetFourVector(W1);
    TLorentzVector newNU2 = Neu2->GetFourVector(W2);
    cout << "Eb1: " << Eb1_top << " " << newB1.E() << endl;
    cout << "Eb2: " << Eb2_top << " " << newB2.E() << endl;
    cout << "El1: " << El1_top << " " << newL1.E() << endl;
    cout << "El2: " << El2_top << " " << newL2.E() << endl;
    cout << "ENU1: " << NU1_top.E() << " " << newNU1.E() << endl;
    cout << "ENU2: " << NU2_top.E() << " " << newNU2.E() << endl;
    
  }
}
void UpsilonMassFit_PolWeights(int iSpec = 3, int PutWeight=1)
{

  double PtCut=4;

  //minbias integrated, |y|<1.2 and |y|\in[1.2,2.4], centrality [0,10][10,20][20,100]%,  pt [0,6.5], [6.5, 10] [10,20]

  gROOT->SetStyle("Plain");
  gStyle->SetPalette(1);
  gStyle->SetFrameBorderMode(0);
  gStyle->SetFrameFillColor(0);
  gStyle->SetCanvasColor(0);
  gStyle->SetTitleFillColor(0);
  gStyle->SetStatColor(0);
  gStyle->SetPadBorderSize(0);
  gStyle->SetCanvasBorderSize(0);
  gStyle->SetOptTitle(1); // at least most of the time
  gStyle->SetOptStat(1); // most of the time, sometimes "nemriou" might be useful to display name, 
  //number of entries, mean, rms, integral, overflow and underflow
  gStyle->SetOptFit(1); // set to 1 only if you want to display fit results

  //==================================== Define Histograms====================================================
  ofstream dataFile(Form("Eff_Upsilon.txt"));
  
  TH1D *diMuonsInvMass_Gen = new TH1D("diMuonsInvMass_Gen","diMuonsInvMass_Gen", 100,8.0,12.0);
  TH1D *diMuonsPt_Gen = new TH1D("diMuonsPt_Gen","diMuonsPt_Gen", 100,0,30);
  //Rapidity Gen
  TH1D *diMuonsRap_Gen0 = new TH1D("diMuonsRap_Gen0","diMuonsRap_Gen0", 100,-5,5);
  TH1D *diMuonsRap_Gen1 = new TH1D("diMuonsRap_Gen1","diMuonsRap_Gen1", 100,-5,5);
  TH1D *diMuonsRap_Gen2 = new TH1D("diMuonsRap_Gen2","diMuonsRap_Gen2", 100,-5,5);
  TH1D *diMuonsRap_Gen3 = new TH1D("diMuonsRap_Gen3","diMuonsRap_Gen3", 100,-5,5);
  TH1D *diMuonsRap_Gen4 = new TH1D("diMuonsRap_Gen4","diMuonsRap_Gen4", 100,-5,5);
  TH1D *diMuonsRap_Gen5 = new TH1D("diMuonsRap_Gen5","diMuonsRap_Gen5", 100,-5,5);
  ////Rapidity Reco
  TH1D *diMuonsRap_Rec0 = new TH1D("diMuonsRap_Rec0","diMuonsRap_Rec0", 100,-5,5);
  diMuonsRap_Rec0->SetLineColor(2);
  TH1D *diMuonsRap_Rec1 = new TH1D("diMuonsRap_Rec1","diMuonsRap_Rec1", 100,-5,5);
  diMuonsRap_Rec1->SetLineColor(2);
  TH1D *diMuonsRap_Rec2 = new TH1D("diMuonsRap_Rec2","diMuonsRap_Rec2", 100,-5,5);
  diMuonsRap_Rec2->SetLineColor(2);
  TH1D *diMuonsRap_Rec3 = new TH1D("diMuonsRap_Rec3","diMuonsRap_Rec3", 100,-5,5);
  diMuonsRap_Rec3->SetLineColor(2);
  TH1D *diMuonsRap_Rec4 = new TH1D("diMuonsRap_Rec4","diMuonsRap_Rec4", 100,-5,5);
  diMuonsRap_Rec4->SetLineColor(2);
  TH1D *diMuonsRap_Rec5 = new TH1D("diMuonsRap_Rec5","diMuonsRap_Rec5", 100,-5,5);
  diMuonsRap_Rec5->SetLineColor(2);
  TH1D *Bin_Gen = new TH1D("Bin_Gen","Bin_Gen", 40,0,40);

  //==============================================Define AccEff Stuff here===========================================
  // Pt bin sizes
  int Nptbin=1;
  double pt_bound[100] = {0};
  if(iSpec == 1) { 
    Nptbin = 5;
    pt_bound[0] = 0;
    pt_bound[1] = 20.0;
    pt_bound[2] = 0.0;
    pt_bound[3] = 6.5;
    pt_bound[4] = 10.0;
    pt_bound[5] = 20.0;
   

    pt_bound[6] = 30.0;
    pt_bound[7] = 35;
    pt_bound[8] = 40;
    pt_bound[9] = 45;
    pt_bound[10] = 50;
  }
  
  if(iSpec == 2) { 
    Nptbin = 2;
    pt_bound[0] = 0.0; 
    pt_bound[1] = 1.2; 
    pt_bound[2] = 2.4; 
    
    pt_bound[3] = 0.0; 
    pt_bound[4] = 0.8; 
    pt_bound[5] = 1.8; 
    //pt_bound[7] = 2.0; 
    pt_bound[6] = 2.4; 
  
  }
  
  
  if(iSpec == 3) {
    Nptbin = 3;
    //for plots
    pt_bound[0] = 0.0;//0
    pt_bound[1] = 4.0;//10
    pt_bound[2] = 8.0;//20
    pt_bound[3] = 40.0;//100
   

    //pt_bound[4] = 16.0;//50
    //pt_bound[5] = 20.0;//100
    //pt_bound[6] = 24.0;
    //pt_bound[7] = 32.0;
    //pt_bound[8] = 40.0;
    //pt_bound[9] = 40.0;
  }
  //X Axis error on Eff graph 
  double PT[100], DelPT[100], mom_err[100];
  for (Int_t ih = 0; ih < Nptbin; ih++) {
    PT[ih] = (pt_bound[ih] + pt_bound[ih+1])/2.0;
    DelPT[ih] = pt_bound[ih+1] - pt_bound[ih];
    mom_err[ih] = DelPT[ih]/2.0;
  }
  
  double genError, recError;
  double gen_pt[100]={0}, gen_ptError[100]={0}; 
  double rec_pt[100]={0}, rec_ptError[100]={0}; 
  double Eff_cat_1[100]={0},Err_Eff_cat_1[100]={0};  
  
  // Histogram arrays
  TH1D *diMuonsInvMass_GenA[10][1000];
  TH1D *diMuonsInvMass_RecA[10][1000];
  TH1D *diMuonsPt_GenA[10][1000];
  TH1D *diMuonsPt_RecA[10][1000];
  char nameGen[10][500], nameRec[10][500], nameGenPt[10][500], nameRecPt[10][500];
 
  
  for (int ifile = 0; ifile <= 5; ifile++) {
    for (Int_t ih = 0; ih < Nptbin; ih++) {
      sprintf(nameGen[ifile],"DiMuonMassGen_pt_%d_%d",ih,ifile);
      sprintf(nameRec[ifile],"DiMuonMassRec_pt_%d_%d",ih,ifile);

      sprintf(nameGenPt[ifile],"DiMuonPtGen_pt_%d_%d",ih,ifile);
      sprintf(nameRecPt[ifile],"DiMuonPtRec_pt_%d_%d",ih,ifile);
      
      diMuonsInvMass_GenA[ifile][ih]= new TH1D(nameGen[ifile],nameGen[ifile],  100,8.0,12.0); //for eff Gen;
      diMuonsInvMass_GenA[ifile][ih]->Sumw2();
      diMuonsInvMass_GenA[ifile][ih]->SetMarkerStyle(7);
      diMuonsInvMass_GenA[ifile][ih]->SetMarkerColor(4);
      diMuonsInvMass_GenA[ifile][ih]->SetLineColor(4);

      diMuonsInvMass_RecA[ifile][ih] = new TH1D(nameRec[ifile],nameRec[ifile], 100,8.0,12.0); //for eff Rec;
      diMuonsInvMass_RecA[ifile][ih]->Sumw2();
      diMuonsInvMass_RecA[ifile][ih]->SetMarkerStyle(8);
      diMuonsInvMass_RecA[ifile][ih]->SetMarkerColor(4);
      diMuonsInvMass_RecA[ifile][ih]->SetLineColor(4);


      diMuonsPt_GenA[ifile][ih]= new TH1D(nameGenPt[ifile],nameGenPt[ifile],  100,0,40); //for eff Gen;
      diMuonsPt_RecA[ifile][ih]= new TH1D(nameRecPt[ifile],nameRecPt[ifile],  100,0,40); //for eff Rec;
    }
  }
  
  //===========================================Input Root File============================================================
  char fileName[10][500];
  //0.0380228 	0.0480769 	0.0293255 	0.0125156 	0.00336587 	0.00276319*2/5 = 0.001105276
  //Scales
  double scale[10]={0};  
  scale[0]=(6.8802); // pT [0-3]
  scale[1]=(8.6995); // pT [3-6]
  scale[2]=(5.3065); // pT [6-9]
  scale[3]=(2.2647); // pT [9-12] 
  scale[4]=(3.0453); // pT [12-15] 
  scale[5]=(1.0000); // pT [15-30]
  
  sprintf(fileName[0],"/home/vineet/HiData/UpsilonData/UpsilonEff/DimuonOnia2Dplots_UpsilonPt03_N.root");
  sprintf(fileName[1],"/home/vineet/HiData/UpsilonData/UpsilonEff/DimuonOnia2Dplots_UpsilonPt36_N.root");
  sprintf(fileName[2],"/home/vineet/HiData/UpsilonData/UpsilonEff/DimuonOnia2Dplots_UpsilonPt69_N.root");
  sprintf(fileName[3],"/home/vineet/HiData/UpsilonData/UpsilonEff/DimuonOnia2Dplots_UpsilonPt912_N.root");
  sprintf(fileName[4],"/home/vineet/HiData/UpsilonData/UpsilonEff/DimuonOnia2Dplots_UpsilonPt1215_N.root");
  sprintf(fileName[5],"/home/vineet/HiData/UpsilonData/UpsilonEff/DimuonOnia2Dplots_UpsilonPt1530_N.root");



  //double scale[10]={0};  
  //scale[0]=(0.0380228/0.001105276);
  //scale[1]=(0.0480769/0.001105276);
  //scale[2]=(0.0293255/0.001105276);
  //scale[3]=(0.0125156/0.001105276);
  //scale[4]=(0.00336587/0.001105276);
  //scale[5]=(0.001105276/0.001105276);
   //34.55 , 43.70 , 26.65 , 11.37 , 3.05 , 1
  //sprintf(fileName[0],"/home/vineet/HiData/UpsilonData/UpsilonEff/DimuonOnia2Dplots_UpsilonPt03.root");
  //sprintf(fileName[1],"/home/vineet/HiData/UpsilonData/UpsilonEff/DimuonOnia2Dplots_UpsilonPt36.root");
  //sprintf(fileName[2],"/home/vineet/HiData/UpsilonData/UpsilonEff/DimuonOnia2Dplots_UpsilonPt69.root");
  //sprintf(fileName[3],"/home/vineet/HiData/UpsilonData/UpsilonEff/DimuonOnia2Dplots_UpsilonPt912.root");
  //sprintf(fileName[4],"/home/vineet/HiData/UpsilonData/UpsilonEff/DimuonOnia2Dplots_UpsilonPt1215.root");
  //sprintf(fileName[5],"/home/vineet/HiData/UpsilonData/UpsilonEff/DimuonOnia2Dplots_UpsilonPt1530.root");
  
  TFile *infile;
  TTree *tree;
  TTree *gentree;
  
  //===========File loop ======================
  
  for(int ifile =0; ifile<=5; ifile++){
    
    infile=new TFile(fileName[ifile],"R");
    tree=(TTree*)infile->Get("SingleMuonTree");
    gentree=(TTree*)infile->Get("SingleGenMuonTree");
    
    //Event variables
    int eventNb,runNb,lumiBlock, gbin, rbin;
    //Jpsi Variables
    Double_t JpsiMass,JpsiPt,JpsiPx,JpsiPy,JpsiPz,JpsiRap, JpsiCharge,JpsiE;
    Double_t JpsiVprob;
    //2.) muon variables RECO                                                                       
    double muPosPx, muPosPy, muPosPz,  muPosEta, muPosPt,muPosP,muPosPhi;
    double muNegPx, muNegPy, muNegPz,  muNegEta, muNegPt,muNegP,muNegPhi;
    //(1).Positive Muon                                     
    double muPos_nchi2In, muPos_dxy, muPos_dz, muPos_nchi2Gl;
    int muPos_found, muPos_pixeLayers, muPos_nValidMuHits,muPos_arbitrated;
    bool muPos_matches,muPos_tracker;
    //(2).Negative Muon                                     
    double muNeg_nchi2In, muNeg_dxy, muNeg_dz, muNeg_nchi2Gl;
    int muNeg_found, muNeg_pixeLayers, muNeg_nValidMuHits,muNeg_arbitrated;
    bool muNeg_matches,muNeg_tracker;
    //Gen Level variables
    //Gen JPsi Variables
    double GenJpsiMass, GenJpsiPt, GenJpsiRap;
    double GenJpsiPx, GenJpsiPy, GenJpsiPz, GenJpsiE;
   
    //2.) Gen muon variables 
    double GenmuPosPx, GenmuPosPy, GenmuPosPz,  GenmuPosEta, GenmuPosPt, GenmuPosPhi;
    double GenmuNegPx, GenmuNegPy, GenmuNegPz,  GenmuNegEta, GenmuNegPt, GenmuNegPhi;

    //Event variables
    tree->SetBranchAddress("eventNb",&eventNb);
    tree->SetBranchAddress("runNb",&runNb);
    tree->SetBranchAddress("lumiBlock",&lumiBlock);
    
    //Jpsi Variables
    tree->SetBranchAddress("JpsiCharge",&JpsiCharge);
    tree->SetBranchAddress("JpsiMass",&JpsiMass);
    tree->SetBranchAddress("JpsiPt",&JpsiPt);
    tree->SetBranchAddress("JpsiPx",&JpsiPx);
    tree->SetBranchAddress("JpsiPy",&JpsiPy);
    tree->SetBranchAddress("JpsiPz",&JpsiPz);
    tree->SetBranchAddress("JpsiRap",&JpsiRap);
    tree->SetBranchAddress("JpsiVprob",&JpsiVprob);
    tree->SetBranchAddress("rbin",&rbin);
    
    //muon variable
    tree->SetBranchAddress("muPosPx",&muPosPx);
    tree->SetBranchAddress("muPosPy",&muPosPy);
    tree->SetBranchAddress("muPosPz",&muPosPz);
    tree->SetBranchAddress("muPosEta",&muPosEta);
    tree->SetBranchAddress("muPosPhi",&muPosPhi);
    tree->SetBranchAddress("muNegPx", &muNegPx);
    tree->SetBranchAddress("muNegPy",    &muNegPy);
    tree->SetBranchAddress("muNegPz",    &muNegPz);
    tree->SetBranchAddress("muNegEta",    &muNegEta);
     tree->SetBranchAddress("muNegPhi", &muNegPhi);

    //1). Positive Muon
    tree->SetBranchAddress("muPos_nchi2In", &muPos_nchi2In);
    tree->SetBranchAddress("muPos_dxy", &muPos_dxy);
    tree->SetBranchAddress("muPos_dz", &muPos_dz);
    tree->SetBranchAddress("muPos_nchi2Gl", &muPos_nchi2Gl);
    tree->SetBranchAddress("muPos_found", &muPos_found);
    tree->SetBranchAddress("muPos_pixeLayers", &muPos_pixeLayers);
    tree->SetBranchAddress("muPos_nValidMuHits", &muPos_nValidMuHits);
    tree->SetBranchAddress("muPos_matches", &muPos_matches);
    tree->SetBranchAddress("muPos_tracker", &muPos_tracker);
    tree->SetBranchAddress("muPos_arbitrated", &muPos_arbitrated);  
    
    //2). Negative Muon                                                                            
    tree->SetBranchAddress("muNeg_nchi2In", &muNeg_nchi2In);
    tree->SetBranchAddress("muNeg_dxy", &muNeg_dxy);
    tree->SetBranchAddress("muNeg_dz", &muNeg_dz);
    tree->SetBranchAddress("muNeg_nchi2Gl", &muNeg_nchi2Gl);
    tree->SetBranchAddress("muNeg_found", &muNeg_found);
    tree->SetBranchAddress("muNeg_pixeLayers", &muNeg_pixeLayers);
    tree->SetBranchAddress("muNeg_nValidMuHits", &muNeg_nValidMuHits);
    tree->SetBranchAddress("muNeg_matches", &muNeg_matches);
    tree->SetBranchAddress("muNeg_tracker", &muNeg_tracker);
    tree->SetBranchAddress("muNeg_arbitrated", &muNeg_arbitrated);
    



//====================================Gen Variables=========================================================
    //Gen Jpsi Variables
    gentree->SetBranchAddress("GenJpsiMass",   &GenJpsiMass);
    gentree->SetBranchAddress("GenJpsiPt",     &GenJpsiPt);
    gentree->SetBranchAddress("GenJpsiRap",    &GenJpsiRap);
    gentree->SetBranchAddress("GenJpsiPx",     &GenJpsiPx);
    gentree->SetBranchAddress("GenJpsiPy",     &GenJpsiPy);
    gentree->SetBranchAddress("GenJpsiPz",     &GenJpsiPz);
    gentree->SetBranchAddress("gbin",&gbin);
    //muon variable
    gentree->SetBranchAddress("GenmuPosPx",    &GenmuPosPx);
    gentree->SetBranchAddress("GenmuPosPy",    &GenmuPosPy);
    gentree->SetBranchAddress("GenmuPosPz",    &GenmuPosPz);
    gentree->SetBranchAddress("GenmuPosEta",    &GenmuPosEta);
     gentree->SetBranchAddress("GenmuPosPhi",    &GenmuPosPhi);
    gentree->SetBranchAddress("GenmuNegPx",    &GenmuNegPx);
    gentree->SetBranchAddress("GenmuNegPy",    &GenmuNegPy);
    gentree->SetBranchAddress("GenmuNegPz",    &GenmuNegPz);
    gentree->SetBranchAddress("GenmuNegEta",    &GenmuNegEta);
    gentree->SetBranchAddress("GenmuNegPhi",    &GenmuNegPhi);

    //====================================================== Gen tree loop ================================================
    int NAccep=0;
    int nGenEntries=gentree->GetEntries();
    cout<<" Total Entries in GenLevel Tree for pT range: "<<fileName[ifile]<<"  "<<   nGenEntries<< " ========="<<endl;
    //dataFile<<" Total Entries in GenLevel Tree for pT range: "<<fileName[ifile]<<"  "<<   nGenEntries<< " ====="<<endl;
    
    
    for(int i=0; i< nGenEntries; i++)  {	    
      gentree->GetEntry(i);
      
      if(i%1000==0){
	cout<<" processing record "<<i<<endl;
	cout<<" Mass "<< GenJpsiMass<< " pT "<< GenJpsiPt << " Y " <<GenJpsiRap<<endl; 
      }
      
      bool GenPosIn=0, GenNegIn=0,GenPosPass=0,GenNegPass=0;

      GenmuPosPt= TMath::Sqrt(GenmuPosPx*GenmuPosPx + GenmuPosPy*GenmuPosPy); 
      GenmuNegPt= TMath::Sqrt(GenmuNegPx*GenmuNegPx + GenmuNegPy*GenmuNegPy); 
      
      GenJpsiE= TMath::Sqrt( GenJpsiPx*GenJpsiPx+GenJpsiPy*GenJpsiPy+GenJpsiPz*GenJpsiPz + 9.46*9.46);


      
      //============================ calculate Pol weight ========================================================================================= //
      Float_t w1,w2,w3,w4,w5;
      // this is the beam energy: 2760GeV->/2->1380GeV each beam
      // the mp=0.938272 is the mass of the proton, as we are looking at p+p collisions
      double E=1380; double pz = sqrt(E*E - 0.938272*0.938272);
      TLorentzVector h1; // beam 1
      TLorentzVector h2; // beam 2
     
      TLorentzVector genJpsi;    // generated upsilon (mother of the single muons) --> if you look at jpsi-> genJpsi (prompt or non-prompt)
      TLorentzVector genMuPlus,genMuMinus; // generator positive muon (charge=+1)
      
      //int mp;
      Float_t cosThetaStarHel; // cosTheta in the Helicity frame
      Float_t cosThetaStarCS;  // cosTheta in the Collins-Soper frame
      TVector3 zCS;             // collins-soper variable

      // put the coordinates of the parent in a TLorentzVector
      // ATTENTION: the last coordinate is the MASS of the parent, which in this case, since it's about Upsilon, it's 9.46
      // when you'll do this for Jpsi, this value has to change to m_jpsi=3.097
      genJpsi.SetPxPyPzE(GenJpsiPx, GenJpsiPy, GenJpsiPz, GenJpsiE); 
      TLorentzRotation boost(-genJpsi.BoostVector()); // boost it
   
      // put the muon in a LorentzVector
      genMuPlus.SetPtEtaPhiM(GenmuPosPt, GenmuPosEta, GenmuPosPhi, 0.106);
      genMuPlus *= boost; // boost it
      
      //genMuMinus.SetPtEtaPhiM(GenmuNegPt, GenmuNegEta, GenmuNegPhi, 0.106);
      //genMuMinus *= boost; // boost it


      //and get the cosTheta in the helicity frame
      cosThetaStarHel = genMuPlus.Vect().Dot(genJpsi.Vect())/(genMuPlus.Vect().Mag()*genJpsi.Vect().Mag());
     
      //int genMuCharge = 1;
      //int mp = genMuCharge>0 ? 0 : 1;
      //cout << genMuCharge << "     " << mp << endl;


      h1.SetPxPyPzE(0,0,pz,E);  // TLorentzVector for beam 1
      h2.SetPxPyPzE(0,0,-pz,E); //  TLorentzVector for beam 2
      h1*=boost;
      h2*=boost;
      // calculate cosTheta CS

      zCS = ( h1.Vect().Unit() - h2.Vect().Unit() ).Unit();
      cosThetaStarCS = genMuPlus.Vect().Dot(zCS)/genMuPlus.Vect().Mag();

      // setup the weights
      w1 = 1;
      w2 = 1 + cosThetaStarHel*cosThetaStarHel;
      w3 = 1 - cosThetaStarHel*cosThetaStarHel;
      w4 = 1 + cosThetaStarCS*cosThetaStarCS;
      w5 = 1 - cosThetaStarCS*cosThetaStarCS;
      

      //w5=1; 

      // cout<<" gen "<<w2<<"   "<<w3<<"  "<<w4<<"  "<<w5<<endl;

      //==============================================================================================================================================//


    
      diMuonsInvMass_Gen->Fill(GenJpsiMass);
      diMuonsPt_Gen->Fill(GenJpsiPt);
 
      if(IsAccept(GenmuPosPt, GenmuPosEta)) {GenPosIn=1;}
      if(IsAccept(GenmuNegPt, GenmuNegEta)) {GenNegIn=1;}
  

    
      if(GenPosIn && GenNegIn ) NAccep++;
      
      if(GenPosIn==1 && GenmuPosPt>PtCut ) {GenPosPass=1;}
      if(GenNegIn==1 && GenmuNegPt>PtCut ) {GenNegPass=1;}

      double GenCenWeight=0,GenWeight=0;
      GenCenWeight=FindCenWeight(gbin);
      Bin_Gen->Fill(gbin);
      GenWeight=GenCenWeight*scale[ifile];
      if(PutWeight==0){GenWeight=1;}

      if(GenPosIn && GenNegIn){
	if(ifile==0){diMuonsRap_Gen0->Fill(GenJpsiRap);}
	if(ifile==1){diMuonsRap_Gen1->Fill(GenJpsiRap);}
	if(ifile==2){diMuonsRap_Gen2->Fill(GenJpsiRap);}
	if(ifile==3){diMuonsRap_Gen3->Fill(GenJpsiRap);}
	if(ifile==4){diMuonsRap_Gen4->Fill(GenJpsiRap);}
	if(ifile==5){diMuonsRap_Gen5->Fill(GenJpsiRap);}
      }
 

      for (Int_t ih = 0; ih < Nptbin; ih++) {
	//adding pT of all pt bins to see diss is cont
	if(iSpec == 1)  if( (GenPosPass==1 && GenNegPass==1) && (TMath::Abs(GenJpsiRap)<2.4 ) && (GenJpsiPt>pt_bound[ih] && GenJpsiPt<=pt_bound[ih+1])){diMuonsPt_GenA[ifile][ih]->Fill(GenJpsiPt,GenWeight*w5);}
	if(iSpec == 1)  if( (GenPosPass==1 && GenNegPass==1) && (TMath::Abs(GenJpsiRap)<2.4 )&&(GenJpsiPt>pt_bound[ih] && GenJpsiPt<=pt_bound[ih+1])){diMuonsInvMass_GenA[ifile][ih]->Fill(GenJpsiMass,GenWeight*w5);}
	if(iSpec == 2)  if((GenPosPass==1 && GenNegPass==1) &&  (GenJpsiPt<20.0) && (TMath::Abs(GenJpsiRap) > pt_bound[ih] && TMath::Abs(GenJpsiRap) <=pt_bound[ih+1] )){diMuonsInvMass_GenA[ifile][ih]->Fill(GenJpsiMass,GenWeight*w5);}
	if(iSpec == 3)  if( (GenPosPass==1 && GenNegPass==1) && (GenJpsiPt < 20.0) &&  (TMath::Abs(GenJpsiRap)<2.4 ) && (gbin>=pt_bound[ih] && gbin<pt_bound[ih+1])){diMuonsInvMass_GenA[ifile][ih]->Fill(GenJpsiMass,GenWeight*w5);}
      

      }

    }//gen loop end
    
    cout<<" accepted no "<< NAccep<<endl;
    //dataFile<<" accepted no "<< NAccep<<endl;
     
    //   new TCanvas;
    //diMuonsInvMass_Gen->Draw();
    //gPad->Print("plots/diMuonsInvMass_Gen.png");
    
    //new TCanvas;
    //diMuonsPt_Gen->Draw();
    //gPad->Print("plots/diMuonsPt_Gen.png");
  
    //new TCanvas;
    //diMuonsRap_Gen0->Draw();
    //sprintf(PlotName,"plots/diMuonsRap_Gen_%d.pdf",ifile);   
    //gPad->Print(PlotName);
    
    //new TCanvas;
    //Bin_Gen->Draw();
    //gPad->Print("plots/Bin_Gen.png");
    
  

    //=============== Rec Tree Loop ==============================================================================
    
    int nRecEntries=tree->GetEntries();
    cout<<"Total Entries in reconstructed Tree for pT range "<<fileName[ifile]<<"  "<<nRecEntries<< "====="<<endl;
    //dataFile<<"Total Entries in reconstructed Tree for pT range "<<fileName[ifile]<<"  "<<nRecEntries<<endl;
    
    for(int i=0; i<nRecEntries; i++)  {	    
      tree->GetEntry(i);
      if(i%100000==0){
	cout<<" processing record "<<i<<endl;
	cout<<" processing Run  " <<runNb <<" event "<<eventNb<<" lum block "<<lumiBlock<<endl;    
	cout<<" Mass "<< JpsiMass<< " pT "<< JpsiPt << " Y " <<JpsiRap<<"  "<<JpsiVprob<<" charge "<<JpsiCharge<<endl; 
      }
      
      bool PosPass=0, NegPass=0, AllCut=0 ,PosIn=0, NegIn=0;
      muPosPt= TMath::Sqrt(muPosPx*muPosPx + muPosPy*muPosPy); 
      muPosP = TMath::Sqrt(muPosPx*muPosPx + muPosPy*muPosPy+ muPosPz*muPosPz); 
      muNegPt= TMath::Sqrt(muNegPx*muNegPx + muNegPy*muNegPy); 
      muNegP = TMath::Sqrt(muNegPx*muNegPx + muNegPy*muNegPy +muNegPz*muNegPz); 
    
      
      JpsiE= TMath::Sqrt(JpsiPx*JpsiPx+JpsiPy*JpsiPy+JpsiPz*JpsiPz + JpsiMass*JpsiMass);
      //============================ calculate Pol weight rec ========================================================================================= //
      Float_t w1=0,w2=0,w3=0,w4=0,w5=0;
      double E=1380; double pz = sqrt(E*E - 0.938272*0.938272);
      TLorentzVector h1; // beam 1
      TLorentzVector h2; // beam 2
      
      TLorentzVector Jpsi;    
      TLorentzVector MuPlus;       
      Float_t cosThetaStarHel; // cosTheta in the Helicity frame
      Float_t cosThetaStarCS;  // cosTheta in the Collins-Soper frame
      TVector3 zCS;             // collins-soper variable
      
      Jpsi.SetPxPyPzE(JpsiPx, JpsiPy, JpsiPz, JpsiE); 
      TLorentzRotation boost(-Jpsi.BoostVector()); // boost it
      
      // put the muon in a LorentzVector
      MuPlus.SetPtEtaPhiM(muPosPt, muPosEta, muPosPhi, 0.106);
      MuPlus *= boost; // boost it
      //and get the cosTheta in the helicity frame
      cosThetaStarHel = MuPlus.Vect().Dot(Jpsi.Vect())/(MuPlus.Vect().Mag()*Jpsi.Vect().Mag());
      h1.SetPxPyPzE(0,0,pz,E);  // TLorentzVector for beam 1
      h2.SetPxPyPzE(0,0,-pz,E); //  TLorentzVector for beam 2
      h1*=boost;
      h2*=boost;
      zCS = ( h1.Vect().Unit() - h2.Vect().Unit() ).Unit();
      cosThetaStarCS = MuPlus.Vect().Dot(zCS)/MuPlus.Vect().Mag();
      // setup the weights
      w1 = 1;
      w2 = 1 + cosThetaStarHel*cosThetaStarHel;
      w3 = 1 - cosThetaStarHel*cosThetaStarHel;
      w4 = 1 + cosThetaStarCS*cosThetaStarCS;
      w5 = 1 - cosThetaStarCS*cosThetaStarCS;
      


      //w5=1;
      //cout<<" rec "<<w2<<"   "<<w3<<"  "<<w4<<"  "<<w5<<endl; 
      //================================================== Pol weights  ===============================================================================//
      
      if(IsAccept(muPosPt, muPosEta)){PosIn=1;}
      if(IsAccept(muNegPt, muNegEta)){NegIn=1;}



      if(muPos_found > 10 && muPos_pixeLayers > 0 && muPos_nchi2In < 4.0 && muPos_dxy < 3 && muPos_dz < 15 && muPos_nchi2Gl < 20 &&  muPos_arbitrated==1 && muPos_tracker==1){PosPass=1;}	  
      
      if(muNeg_found >10 && muNeg_pixeLayers >0 && muNeg_nchi2In <4.0 && muNeg_dxy < 3 && muNeg_dz < 15 && muNeg_nchi2Gl < 20 && muNeg_arbitrated==1 && muNeg_tracker==1){NegPass=1;}

      // cout<<muPos_matches<<"  "<<muNeg_matches<<endl;
      
      if((muPosPt > PtCut && muNegPt > PtCut) && (muPos_matches==1 && muNeg_matches==1) && (PosIn==1 && NegIn==1 )  &&   (PosPass==1 && NegPass==1)){AllCut=1;}
    
      double RecCenWeight=0,RecWeight=0;
      RecCenWeight=FindCenWeight(rbin);
      RecWeight=RecCenWeight*scale[ifile];
      if(PutWeight==0){RecWeight=1;}
     
      if(i%100000==0){
	cout<<" eff loop for reco "<<endl;
      }
      
      if(AllCut==1){
	if(ifile==0){diMuonsRap_Rec0->Fill(JpsiRap);}
	if(ifile==1){diMuonsRap_Rec1->Fill(JpsiRap);}
	if(ifile==2){diMuonsRap_Rec2->Fill(JpsiRap);}
	if(ifile==3){diMuonsRap_Rec3->Fill(JpsiRap);}
	if(ifile==4){diMuonsRap_Rec4->Fill(JpsiRap);}
	if(ifile==5){diMuonsRap_Rec5->Fill(JpsiRap);}
      }

      //Eff loop for reco
      if((JpsiCharge == 0) && (JpsiVprob > 0.01)) {
	for (Int_t ih = 0; ih < Nptbin; ih++) {
	  //to see cont reco pT
	  if(iSpec == 1)if((AllCut==1) && (TMath::Abs(JpsiRap) < 2.4) && (JpsiPt>pt_bound[ih] && JpsiPt<=pt_bound[ih+1])) {diMuonsPt_RecA[ifile][ih]->Fill(JpsiPt,RecWeight*w5);}
	  
	  if(iSpec == 1)if((AllCut==1) && (TMath::Abs(JpsiRap)<2.4 ) && (JpsiPt > pt_bound[ih] && JpsiPt <=pt_bound[ih+1])){diMuonsInvMass_RecA[ifile][ih]->Fill(JpsiMass, RecWeight*w5);}
	  if(iSpec == 2) if( (AllCut==1) &&  (JpsiPt<20.0) && (TMath::Abs(JpsiRap) > pt_bound[ih] && TMath::Abs(JpsiRap) <=pt_bound[ih+1])){diMuonsInvMass_RecA[ifile][ih]->Fill(JpsiMass,RecWeight*w5);}
	  if(iSpec == 3) if((AllCut==1) &&  (JpsiPt<20.0) && (TMath::Abs(JpsiRap) < 2.4) && (rbin>=pt_bound[ih] &&  rbin < pt_bound[ih+1])){diMuonsInvMass_RecA[ifile][ih]->Fill(JpsiMass,RecWeight*w5);}
	



	}
      }
    }
  
    /*
    new TCanvas;
    if(ifile==0){diMuonsRap_Gen0->Draw();new TCanvas; diMuonsRap_Rec0->Draw(); gPad->Print("plots/NPdiMuonsRap_Gen0.png");}
    if(ifile==1){diMuonsRap_Gen1->Draw();new TCanvas; diMuonsRap_Rec1->Draw(); gPad->Print("plots/NPdiMuonsRap_Gen1.png");}
    if(ifile==2){diMuonsRap_Gen2->Draw();new TCanvas; diMuonsRap_Rec2->Draw(); gPad->Print("plots/NPdiMuonsRap_Gen2.png");}
    if(ifile==3){diMuonsRap_Gen3->Draw();new TCanvas; diMuonsRap_Rec3->Draw(); gPad->Print("plots/NPdiMuonsRap_Gen3.png");}
    if(ifile==4){diMuonsRap_Gen4->Draw();new TCanvas; diMuonsRap_Rec4->Draw(); gPad->Print("plots/NPdiMuonsRap_Gen4.png");}
    if(ifile==5){diMuonsRap_Gen5->Draw();new TCanvas; diMuonsRap_Rec5->Draw(); gPad->Print("plots/NPdiMuonsRap_Gen5.png");}
    */
  }  // file loop ends 

  ///////////////////////////////////////////////////////////////////

  cout<< " adding "<<endl;
  TH1D *diMuonsInvMass_RecA1[100];
  TH1D *diMuonsInvMass_GenA1[100];
  TH1D *diMuonsPt_GenA1[100];
  TH1D *diMuonsPt_RecA1[100];
  TF1 *backfun_1;
  char namePt_1B[500];//for bkg func
 
  for(Int_t ih = 0; ih < Nptbin; ih++){
    diMuonsInvMass_RecA1[ih] = diMuonsInvMass_RecA[0][ih];
    diMuonsInvMass_GenA1[ih] = diMuonsInvMass_GenA[0][ih];
    diMuonsPt_GenA1[ih] = diMuonsPt_GenA[0][ih];
    diMuonsPt_RecA1[ih] = diMuonsPt_RecA[0][ih];
    
    for (int ifile = 1; ifile <= 5; ifile++) {
      diMuonsInvMass_RecA1[ih]->Add(diMuonsInvMass_RecA[ifile][ih]);
      diMuonsInvMass_GenA1[ih]->Add(diMuonsInvMass_GenA[ifile][ih]);     
      
      diMuonsPt_GenA1[ih]->Add(diMuonsPt_GenA[ifile][ih]); 
      diMuonsPt_RecA1[ih]->Add(diMuonsPt_RecA[ifile][ih]); 
    }
  }
  
  //===========================Fitting===================================================================//
  // Fit ranges
  double mass_low, mass_high;
  double MassUpsilon, WeidthUpsilon;
  
  // Low mass range upsilon width 54 KeV
  MassUpsilon = 9.46; WeidthUpsilon = 0.055;
  //MassUpsilon = 9.46; WeidthUpsilon = 0.068;
  mass_low = 9.0; mass_high = 10.0;  // Fit ranges
  
  // Fit Function crystall ball
  TF1 *GAUSPOL = new TF1("GAUSPOL",CrystalBall,8.0,12.0,6);
  GAUSPOL->SetParNames("Yield (#Upsilon)","BinWidth","Mean","Sigma","#alpha","n");
  GAUSPOL->SetParameter(2, MassUpsilon);
  GAUSPOL->SetParameter(3, WeidthUpsilon);
  //GAUSPOL->SetParLimits(3, 0.1*WeidthUpsilon,2.0*WeidthUpsilon);
  GAUSPOL->SetParameter(4, 1.0);
  GAUSPOL->SetParameter(5, 20.0);
  GAUSPOL->SetLineWidth(2.0);
  GAUSPOL->SetLineColor(2);




  //=====================Loop for eff===========================================================
  double GenNo[100]={0};
  double Eff[100]={0};
  double GenError[100]={0};
  double RecError[100]={0};
  double errEff_cat_S1[100]={0};
  double errEff_cat_S2[100]={0};
  double errEff_cat_S1_1[100]={0},errEff_cat_S1_2[100]={0};
  double errEff_cat_S2_1[100]={0},errEff_cat_S2_2[100]={0};
  char PlotName[500],PlotName1[500], PlotName2[500]; 
  char GPlotName[500],GPlotName1[500], GPlotName2[500];

  for (Int_t ih = 0; ih < Nptbin; ih++) {
   
    cout<<" no of gen dimuons from diMuons Pt histo    "<<diMuonsPt_GenA1[ih]->Integral(1,100)<<endl;
    cout<<" no of gen dimuons from diMuons Mass histo  "<<diMuonsInvMass_GenA1[ih]->Integral(1,100)<<endl;
    

    //from pT histogram
    //gen_pt[ih] =diMuonsPt_GenA1[ih]->IntegralAndError(1,100,genError);
   
    gen_pt[ih] = diMuonsInvMass_GenA1[ih]->IntegralAndError(1,100,genError);
    gen_ptError[ih]= genError;
    
    if(iSpec==1) sprintf(PlotName,"plots/DiMuonMass_PtBin_%d.png",ih);
    if(iSpec==2) sprintf(PlotName,"plots/DiMuonMass_RapBin_%d.png",ih);
    if(iSpec==3) sprintf(PlotName,"plots/DiMuonMass_CentBin_%d.png",ih);
    
    if(iSpec==1) sprintf(PlotName1,"plots/DiMuonMass_PtBin_%d.pdf",ih);
    if(iSpec==2) sprintf(PlotName1,"plots/DiMuonMass_RapBin_%d.pdf",ih);
    if(iSpec==3) sprintf(PlotName1,"plots/DiMuonMass_CentBin_%d.pdf",ih);
    
    if(iSpec==1) sprintf(PlotName2,"plots/DiMuonMass_PtBin_%d.eps",ih);
    if(iSpec==2) sprintf(PlotName2,"plots/DiMuonMass_RapBin_%d.eps",ih);
    if(iSpec==3) sprintf(PlotName2,"plots/DiMuonMass_CentBin_%d.eps",ih);
 

    //giving inetial value for crystall ball fourth parameter 
    diMuonsInvMass_RecA1[ih]->Rebin(2);
    GAUSPOL->SetParameter(0, diMuonsInvMass_RecA1[ih]->Integral(0,50));
    GAUSPOL->FixParameter(1, diMuonsInvMass_RecA1[ih]->GetBinWidth(1));
    
    new TCanvas; 
    diMuonsInvMass_RecA1[ih]->Fit("GAUSPOL","LLMERQ", "", mass_low, mass_high);
   
    double UpsilonMass = GAUSPOL->GetParameter(2);
    double UpsilonWidth = GAUSPOL->GetParameter(3);
   
    double UpsilonYield = GAUSPOL->GetParameter(0);
    double UpsilonYieldError = GAUSPOL->GetParError(0);
 
    double par[20];
    GAUSPOL->GetParameters(par);
    sprintf(namePt_1B,"pt_1B_%d",ih);
    backfun_1 = new TF1(namePt_1B, Pol2, mass_low, mass_high, 3);
    backfun_1->SetParameters(&par[4]);
   

    double MassLow=(UpsilonMass-3*UpsilonWidth);
    double MassHigh=(UpsilonMass+3*UpsilonWidth);
    
    int binlow =diMuonsInvMass_RecA1[ih]->GetXaxis()->FindBin(MassLow);
    int binhi =diMuonsInvMass_RecA1[ih]->GetXaxis()->FindBin(MassHigh);
    double binwidth=diMuonsInvMass_RecA1[ih]->GetBinWidth(1);
        
    //yield by function 
    //rec_pt[ih] = UpsilonYield;
    //rec_ptError[ih]= UpsilonYieldError;

    cout<<"Rec diMuons from Pt histo "<<diMuonsPt_RecA1[ih]->Integral(1,100)<<endl;  
    cout<<"Rec dimuons from mass "<<diMuonsInvMass_RecA1[ih]->Integral(1,100)<<endl; 
    

      
    //from pT histo
    //rec_pt[ih]=diMuonsPt_RecA1[ih]->IntegralAndError(1, 100,recError);

    //yield by histogram integral
    rec_pt[ih] = diMuonsInvMass_RecA1[ih]->IntegralAndError(binlow, binhi,recError);
    rec_ptError[ih]= recError;
  
    //Cal eff 
    Eff_cat_1[ih] = rec_pt[ih]/gen_pt[ih]; 
  
    //calculate error on eff
    GenNo[ih]=gen_pt[ih];
    Eff[ih]= Eff_cat_1[ih];
    GenError[ih]=gen_ptError[ih];
    RecError[ih]=rec_ptError[ih];
    //error    
    errEff_cat_S1_1[ih]= ( (Eff[ih] * Eff[ih]) /(GenNo[ih] * GenNo[ih]) );
    errEff_cat_S1_2[ih]= (RecError[ih] * RecError[ih]);
    errEff_cat_S1[ih]= (errEff_cat_S1_1[ih] * errEff_cat_S1_2[ih]);
   

    errEff_cat_S2_1[ih]= ( (1 - Eff[ih])* (1 - Eff[ih]) ) / ( GenNo[ih] * GenNo[ih]);
    errEff_cat_S2_2[ih]= (GenError[ih] * GenError[ih] ) - ( RecError[ih] * RecError[ih] );


    errEff_cat_S2[ih]=errEff_cat_S2_1[ih]*errEff_cat_S2_2[ih];
   

    Err_Eff_cat_1[ih]=sqrt(errEff_cat_S1[ih] + errEff_cat_S2[ih]);
   
    //error for no weights
    //Err_Eff_cat_1[ih]= Eff_cat_1[ih]*TMath::Sqrt(gen_ptError[ih]*gen_ptError[ih]/(gen_pt[ih]*gen_pt[ih]) + rec_ptError[ih]*rec_ptError[ih]/(rec_pt[ih]* rec_pt[ih]));

    cout<<"Upsilon Yield by integral of histo:  "<< diMuonsInvMass_RecA1[ih]->IntegralAndError(binlow, binhi,recError) <<"  error "<< rec_ptError[ih]<<endl; 
    cout<<"UpsilonYield by Gauss yield det:     "<< UpsilonYield << " UpsilonWidth "<< UpsilonWidth<<" UpsilonMass "<<UpsilonMass <<endl;
    cout<<"Upsilon Yield by Function integral:  "<< GAUSPOL->Integral(MassLow,MassHigh)/binwidth <<endl;
    cout<<" rec_pt[ih]  "<<  rec_pt[ih] <<" gen_pt[ih] "<<gen_pt[ih]<<endl;
    //dataFile<<" rec_pt[ih]  "<<  rec_pt[ih] <<" gen_pt[ih] "<<gen_pt[ih]<<endl;
    cout<<" eff "<< Eff_cat_1[ih]<<" error "<<Err_Eff_cat_1[ih]<<endl;
    
    dataFile<<"ih " <<ih<<" eff "<< Eff_cat_1[ih]<<" error "<<Err_Eff_cat_1[ih]<<endl;
    
    if(iSpec==1) sprintf(GPlotName,"plots/GenDiMuonMass_PtBin_%d.png",ih);
    if(iSpec==2) sprintf(GPlotName,"plots/GenDiMuonMass_RapBin_%d.png",ih);
    if(iSpec==3) sprintf(GPlotName,"plots/GenDiMuonMass_CentBin_%d.png",ih);
    
    if(iSpec==1) sprintf(GPlotName1,"plots/GenDiMuonMass_PtBin_%d.pdf",ih);
    if(iSpec==2) sprintf(GPlotName1,"plots/GenDiMuonMass_RapBin_%d.pdf",ih);
    if(iSpec==3) sprintf(GPlotName1,"plots/GenDiMuonMass_CentBin_%d.pdf",ih);
    
    if(iSpec==1) sprintf(GPlotName2,"plots/GenDiMuonMass_PtBin_%d.eps",ih);
    if(iSpec==2) sprintf(GPlotName2,"plots/GenDiMuonMass_RapBin_%d.eps",ih);
    if(iSpec==3) sprintf(GPlotName2,"plots/GenDiMuonMass_CentBin_%d.eps",ih);
       
    backfun_1->SetLineColor(4);
    backfun_1->SetLineWidth(1);
    //backfun_1->Draw("same");
    gPad->Print(PlotName);
    gPad->Print(PlotName1);
    gPad->Print(PlotName2);

    new TCanvas;
    diMuonsInvMass_GenA1[ih]->Draw();
    gPad->Print(GPlotName);
    gPad->Print(GPlotName1);
    gPad->Print(GPlotName2);


    //new TCanvas;
    //diMuonsPt_GenA1[ih]->Draw();
    //new TCanvas;
    //diMuonsPt_RecA1[ih]->Draw();
 
}
  dataFile.close();

  TGraphErrors *Eff_Upsilon = new TGraphErrors(Nptbin, PT, Eff_cat_1, mom_err,Err_Eff_cat_1);
  Eff_Upsilon->SetMarkerStyle(21);
  Eff_Upsilon->SetMarkerColor(2);
  Eff_Upsilon->GetYaxis()->SetTitle("Reco Eff");
 
  if(iSpec==1) Eff_Upsilon->GetXaxis()->SetTitle("#Upsilon pT (GeV/c^{2})");
  if(iSpec==2) Eff_Upsilon->GetXaxis()->SetTitle("#Upsilon rapidity");
  if(iSpec==3) Eff_Upsilon->GetXaxis()->SetTitle("bin");
   Eff_Upsilon->GetYaxis()->SetRangeUser(0,1.0);

  TLegend *legend_GP = new TLegend( 0.50,0.79,0.80,0.89);
  legend_GP->SetBorderSize(0);
  legend_GP->SetFillStyle(0);
  legend_GP->SetFillColor(0);
  legend_GP->SetTextSize(0.032);
  legend_GP->AddEntry(Eff_Upsilon,"PythiaEvtGen + HydjetBass", "P");
  
  new TCanvas;
  Eff_Upsilon->Draw("AP");
  legend_GP->Draw("Same");
    
  if(iSpec==1){ gPad->Print("plots/Eff_Upsilon_Pt.pdf");gPad->Print("plots/Eff_Upsilon_Pt.png");gPad->Print("plots/Eff_Upsilon_Pt.eps");}
  if(iSpec==2){ gPad->Print("plots/Eff_Upsilon_Rap.pdf");gPad->Print("plots/Eff_Upsilon_Rap.png");  gPad->Print("plots/Eff_Upsilon_Rap.eps");}
  if(iSpec==3){ gPad->Print("plots/Eff_Upsilon_Cent.pdf");gPad->Print("plots/Eff_Upsilon_Cent.png"); gPad->Print("plots/Eff_Upsilon_Cent.eps"); }

}
Exemple #20
0
void computeAngles(TLorentzVector thep4H, TLorentzVector thep4Z1, TLorentzVector thep4M11, TLorentzVector thep4M12, TLorentzVector thep4Z2, TLorentzVector thep4M21, TLorentzVector thep4M22, double& costheta1, double& costheta2, double& Phi, double& costhetastar, double& Phi1){
       
  ///////////////////////////////////////////////
  // check for z1/z2 convention, redefine all 4 vectors with convention
  ///////////////////////////////////////////////
  TLorentzVector p4H, p4Z1, p4M11, p4M12, p4Z2, p4M21, p4M22;
  p4H = thep4H;
        
  p4Z1 = thep4Z1; p4M11 = thep4M11; p4M12 = thep4M12;
  p4Z2 = thep4Z2; p4M21 = thep4M21; p4M22 = thep4M22;
  //// costhetastar
  TVector3 boostX = -(thep4H.BoostVector());
  TLorentzVector thep4Z1inXFrame( p4Z1 );
  TLorentzVector thep4Z2inXFrame( p4Z2 );
  thep4Z1inXFrame.Boost( boostX );
  thep4Z2inXFrame.Boost( boostX );
  TVector3 theZ1X_p3 = TVector3( thep4Z1inXFrame.X(), thep4Z1inXFrame.Y(), thep4Z1inXFrame.Z() );
  TVector3 theZ2X_p3 = TVector3( thep4Z2inXFrame.X(), thep4Z2inXFrame.Y(), thep4Z2inXFrame.Z() );    
  costhetastar = theZ1X_p3.CosTheta();

  //// --------------------------- costheta1
  TVector3 boostV1 = -(thep4Z1.BoostVector());
  TLorentzVector p4M11_BV1( p4M11 );
  TLorentzVector p4M12_BV1( p4M12 );
  TLorentzVector p4M21_BV1( p4M21 );
  TLorentzVector p4M22_BV1( p4M22 );
  p4M11_BV1.Boost( boostV1 );
  p4M12_BV1.Boost( boostV1 );
  p4M21_BV1.Boost( boostV1 );
  p4M22_BV1.Boost( boostV1 );
    
  TLorentzVector p4V2_BV1 = p4M21_BV1 + p4M22_BV1;
  //// costheta1
  costheta1 = -p4V2_BV1.Vect().Dot( p4M11_BV1.Vect() )/p4V2_BV1.Vect().Mag()/p4M11_BV1.Vect().Mag();

  //// --------------------------- costheta2
  TVector3 boostV2 = -(thep4Z2.BoostVector());
  TLorentzVector p4M11_BV2( p4M11 );
  TLorentzVector p4M12_BV2( p4M12 );
  TLorentzVector p4M21_BV2( p4M21 );
  TLorentzVector p4M22_BV2( p4M22 );
  p4M11_BV2.Boost( boostV2 );
  p4M12_BV2.Boost( boostV2 );
  p4M21_BV2.Boost( boostV2 );
  p4M22_BV2.Boost( boostV2 );
    
  TLorentzVector p4V1_BV2 = p4M11_BV2 + p4M12_BV2;
  //// costheta2
  costheta2 = -p4V1_BV2.Vect().Dot( p4M21_BV2.Vect() )/p4V1_BV2.Vect().Mag()/p4M21_BV2.Vect().Mag();
    
  //// --------------------------- Phi and Phi1 (old phistar1 - azimuthal production angle)
  //    TVector3 boostX = -(thep4H.BoostVector());
  TLorentzVector p4M11_BX( p4M11 );
  TLorentzVector p4M12_BX( p4M12 );
  TLorentzVector p4M21_BX( p4M21 );
  TLorentzVector p4M22_BX( p4M22 );
    
  p4M11_BX.Boost( boostX );
  p4M12_BX.Boost( boostX );
  p4M21_BX.Boost( boostX );
  p4M22_BX.Boost( boostX );
    
  TVector3 tmp1 = p4M11_BX.Vect().Cross( p4M12_BX.Vect() );
  TVector3 tmp2 = p4M21_BX.Vect().Cross( p4M22_BX.Vect() );    
    
  TVector3 normal1_BX( tmp1.X()/tmp1.Mag(), tmp1.Y()/tmp1.Mag(), tmp1.Z()/tmp1.Mag() ); 
  TVector3 normal2_BX( tmp2.X()/tmp2.Mag(), tmp2.Y()/tmp2.Mag(), tmp2.Z()/tmp2.Mag() ); 

  //// Phi
  TLorentzVector p4Z1_BX = p4M11_BX + p4M12_BX;    
  double tmpSgnPhi = p4Z1_BX.Vect().Dot( normal1_BX.Cross( normal2_BX) );
  double sgnPhi = tmpSgnPhi/fabs(tmpSgnPhi);
  Phi = sgnPhi * acos( -1.*normal1_BX.Dot( normal2_BX) );
    
    
  //////////////
    
  TVector3 beamAxis(0,0,1);
  TVector3 tmp3 = (p4M11_BX + p4M12_BX).Vect();
    
  TVector3 p3V1_BX( tmp3.X()/tmp3.Mag(), tmp3.Y()/tmp3.Mag(), tmp3.Z()/tmp3.Mag() );
  TVector3 tmp4 = beamAxis.Cross( p3V1_BX );
  TVector3 normalSC_BX( tmp4.X()/tmp4.Mag(), tmp4.Y()/tmp4.Mag(), tmp4.Z()/tmp4.Mag() );
        
  //// Phi1
  double tmpSgnPhi1 = p4Z1_BX.Vect().Dot( normal1_BX.Cross( normalSC_BX) );
  double sgnPhi1 = tmpSgnPhi1/fabs(tmpSgnPhi1);    
  Phi1 = sgnPhi1 * acos( normal1_BX.Dot( normalSC_BX) );    
    
  //    std::cout << "extractAngles: " << std::endl;
  //    std::cout << "costhetastar = " << costhetastar << ", costheta1 = " << costheta1 << ", costheta2 = " << costheta2 << std::endl;
  //    std::cout << "Phi = " << Phi << ", Phi1 = " << Phi1 << std::endl;    

}
Exemple #21
0
void NewVariables(){

  const double protonmass = 938.272013; //MeV
  const double pionmass = 139.57018; //MeV
  const double kaonmass = 493.677; //MeV
  //const double muonmass = 105.6583715; //MeV

  TStopwatch *clock = new TStopwatch();
  clock->Start(1);

  double p_PT, p_ETA, p_PHI;
  double K_PT, K_ETA, K_PHI;
  double pi_PT, pi_ETA, pi_PHI;
  double Xb_OWNPV_X, Xb_OWNPV_Y, Xb_OWNPV_Z;
  double Xb_ENDVERTEX_X, Xb_ENDVERTEX_Y, Xb_ENDVERTEX_Z;
  double Xb_PT, Xb_ETA, Xb_PHI, Xb_M;
  double Xc_PT, Xc_ETA, Xc_PHI, Xc_M;
  float Added_H_PT[200], Added_H_ETA[200], Added_H_PHI[200];
  int Added_n_Particles;

  gErrorIgnoreLevel = kError;
  TFile *fSLBS = new TFile("/auto/data/mstahl/SLBaryonSpectroscopy/SLBaryonSpectroscopyStrp21.root","read");
  TTree *Xic_tree = (TTree*)gDirectory->Get("Xib02XicMuNu/Xic2pKpi/DecayTree");
  gErrorIgnoreLevel = kPrint;
  Xic_tree->SetBranchStatus("*",0); //disable all branches
  //now switch on the ones we need (saves a lot of time)  
  Xic_tree->SetBranchStatus("Xib_M",1);
  Xic_tree->SetBranchStatus("Xib_PT",1);
  Xic_tree->SetBranchStatus("Xib_ETA",1);
  Xic_tree->SetBranchStatus("Xib_PHI",1);
  Xic_tree->SetBranchStatus("Xib_OWNPV_X",1);
  Xic_tree->SetBranchStatus("Xib_OWNPV_Y",1);
  Xic_tree->SetBranchStatus("Xib_OWNPV_Z",1);
  Xic_tree->SetBranchStatus("Xib_ENDVERTEX_X",1);
  Xic_tree->SetBranchStatus("Xib_ENDVERTEX_Y",1);
  Xic_tree->SetBranchStatus("Xib_ENDVERTEX_Z",1);

  Xic_tree->SetBranchStatus("Xic_M",1);
  Xic_tree->SetBranchStatus("Xic_PT",1);
  Xic_tree->SetBranchStatus("Xic_ETA",1);
  Xic_tree->SetBranchStatus("Xic_PHI",1);

  Xic_tree->SetBranchStatus("Added_n_Particles",1);
  Xic_tree->SetBranchStatus("Added_H_PT",1);
  Xic_tree->SetBranchStatus("Added_H_ETA",1);
  Xic_tree->SetBranchStatus("Added_H_PHI",1);

  Xic_tree->SetBranchStatus("p_PT",1);
  Xic_tree->SetBranchStatus("p_ETA",1);
  Xic_tree->SetBranchStatus("p_PHI",1);
  Xic_tree->SetBranchStatus("K_PT",1);
  Xic_tree->SetBranchStatus("K_ETA",1);
  Xic_tree->SetBranchStatus("K_PHI",1);
  Xic_tree->SetBranchStatus("pi_PT",1);
  Xic_tree->SetBranchStatus("pi_ETA",1);
  Xic_tree->SetBranchStatus("pi_PHI",1);

  //set the branch addresses
  Xic_tree->SetBranchAddress("Xib_M",&Xb_M);
  Xic_tree->SetBranchAddress("Xib_PT",&Xb_PT);
  Xic_tree->SetBranchAddress("Xib_ETA",&Xb_ETA);
  Xic_tree->SetBranchAddress("Xib_PHI",&Xb_PHI);
  Xic_tree->SetBranchAddress("Xib_OWNPV_X",&Xb_OWNPV_X);
  Xic_tree->SetBranchAddress("Xib_OWNPV_Y",&Xb_OWNPV_Y);
  Xic_tree->SetBranchAddress("Xib_OWNPV_Z",&Xb_OWNPV_Z);
  Xic_tree->SetBranchAddress("Xib_ENDVERTEX_X",&Xb_ENDVERTEX_X);
  Xic_tree->SetBranchAddress("Xib_ENDVERTEX_Y",&Xb_ENDVERTEX_Y);
  Xic_tree->SetBranchAddress("Xib_ENDVERTEX_Z",&Xb_ENDVERTEX_Z);

  Xic_tree->SetBranchAddress("Xic_M",&Xc_M);
  Xic_tree->SetBranchAddress("Xic_PT",&Xc_PT);
  Xic_tree->SetBranchAddress("Xic_ETA",&Xc_ETA);
  Xic_tree->SetBranchAddress("Xic_PHI",&Xc_PHI);

  Xic_tree->SetBranchAddress("Added_n_Particles",&Added_n_Particles);
  Xic_tree->SetBranchAddress("Added_H_PT",&Added_H_PT);
  Xic_tree->SetBranchAddress("Added_H_ETA",&Added_H_ETA);
  Xic_tree->SetBranchAddress("Added_H_PHI",&Added_H_PHI);

  Xic_tree->SetBranchAddress("p_PT",&p_PT);
  Xic_tree->SetBranchAddress("p_ETA",&p_ETA);
  Xic_tree->SetBranchAddress("p_PHI",&p_PHI);
  Xic_tree->SetBranchAddress("K_PT",&K_PT);
  Xic_tree->SetBranchAddress("K_ETA",&K_ETA);
  Xic_tree->SetBranchAddress("K_PHI",&K_PHI);
  Xic_tree->SetBranchAddress("pi_PT",&pi_PT);
  Xic_tree->SetBranchAddress("pi_ETA",&pi_ETA);
  Xic_tree->SetBranchAddress("pi_PHI",&pi_PHI);
  //SLBS_tree->AddBranchToCache("*");
  //SLBS_tree->LoadBaskets(1000000000);//Load baskets up to 1 GB to memory

  double Xb_CorrM, p_beta, K_beta, pi_beta;
  float Xcpi_CosTheta[200],XcK_CosTheta[200],Xcp_CosTheta[200];
  double p_as_piKpi_M, p_as_KKpi_M, pK_as_pipi_M, pK_as_ppi_M, pKpi_as_K_M, pKpi_as_p_M;

  TFile *f1 = new TFile("/auto/data/mstahl/SLBaryonSpectroscopy/SLBaryonSpectroscopyStrp21_friend.root","RECREATE");
  //f1->mkdir("Xib02XicMuNu/Xic2pKpi");
  //f1->cd("Xib02XicMuNu/Xic2pKpi");
  TTree added_Xic_tree("Xic2pKpi","Xic2pKpi");

  added_Xic_tree.Branch("Xib_CorrM", &Xb_CorrM, "Xib_CorrM/D");
  added_Xic_tree.Branch("p_beta", &p_beta, "p_beta/D");
  added_Xic_tree.Branch("K_beta", &K_beta, "K_beta/D");
  added_Xic_tree.Branch("pi_beta", &pi_beta, "pi_beta/D");
  added_Xic_tree.Branch("Added_n_Particles", &Added_n_Particles, "Added_n_Particles/I");
  added_Xic_tree.Branch("Xcpi_CosTheta", &Xcpi_CosTheta, "Xcpi_CosTheta[Added_n_Particles]/F");
  added_Xic_tree.Branch("XcK_CosTheta", &XcK_CosTheta, "XcK_CosTheta[Added_n_Particles]/F");
  added_Xic_tree.Branch("Xcp_CosTheta", &Xcp_CosTheta, "Xcp_CosTheta[Added_n_Particles]/F");
  added_Xic_tree.Branch("p_as_piKpi_M", &p_as_piKpi_M, "p_as_piKpi_M/D");
  added_Xic_tree.Branch("p_as_KKpi_M", &p_as_KKpi_M, "p_as_KKpi_M/D");
  added_Xic_tree.Branch("pK_as_pipi_M", &pK_as_pipi_M, "pK_as_pipi_M/D");
  added_Xic_tree.Branch("pK_as_ppi_M", &pK_as_ppi_M, "pK_as_ppi_M/D");
  added_Xic_tree.Branch("pKpi_as_K_M", &pKpi_as_K_M, "pKpi_as_K_M/D");
  added_Xic_tree.Branch("pKpi_as_p_M", &pKpi_as_p_M, "pKpi_as_p_M/D");

  UInt_t Xic_nevents = Xic_tree->GetEntries();
  cout << "Entries in Xic tree: " << Xic_nevents << endl;

  for (UInt_t evt = 0; evt < Xic_nevents;evt++) {
    Xic_tree->GetEntry(evt);

    TVector3 dir(Xb_ENDVERTEX_X-Xb_OWNPV_X,Xb_ENDVERTEX_Y-Xb_OWNPV_Y,Xb_ENDVERTEX_Z-Xb_OWNPV_Z);
    TVector3 mom;
    mom.SetPtEtaPhi(Xb_PT,Xb_ETA,Xb_PHI);
    double dmag2 = dir.Mag2();
    double ptprime = 0;
    if ( 0 == dmag2 ) ptprime = mom.Mag();
    else ptprime = (mom - dir * ( mom.Dot( dir ) / dmag2 )).Mag() ;
    Xb_CorrM = sqrt(Xb_M*Xb_M + ptprime*ptprime) + ptprime;

    TLorentzVector Xb;
    Xb.SetPtEtaPhiM(Xb_PT,Xb_ETA,Xb_PHI,Xb_CorrM);
    TLorentzVector Xc;
    Xc.SetPtEtaPhiM(Xc_PT,Xc_ETA,Xc_PHI,Xc_M);
    for(int i = 0; i < Added_n_Particles; i++){
      TLorentzVector Hpi;
      Hpi.SetPtEtaPhiM(Added_H_PT[i],Added_H_ETA[i],Added_H_PHI[i],pionmass);
      TLorentzVector HK;
      HK.SetPtEtaPhiM(Added_H_PT[i],Added_H_ETA[i],Added_H_PHI[i],kaonmass);
      TLorentzVector Hp;
      Hp.SetPtEtaPhiM(Added_H_PT[i],Added_H_ETA[i],Added_H_PHI[i],protonmass);
      TLorentzVector Xcpi = Hpi + Xc;
      TLorentzVector XcK = HK + Xc;
      TLorentzVector Xcp = Hp + Xc;
      Xcpi.Boost(-Xb.BoostVector());
      Xcpi_CosTheta[i] = cos(Xcpi.Angle(Xb.Vect()));
      XcK.Boost(-Xb.BoostVector());
      XcK_CosTheta[i] = cos(XcK.Angle(Xb.Vect()));
      Xcp.Boost(-Xb.BoostVector());
      Xcp_CosTheta[i] = cos(Xcp.Angle(Xb.Vect()));
    }

    TLorentzVector proton;
    proton.SetPtEtaPhiM(p_PT,p_ETA,p_PHI,protonmass);
    TLorentzVector kaon;
    kaon.SetPtEtaPhiM(K_PT,K_ETA,K_PHI,kaonmass);
    TLorentzVector pion;
    pion.SetPtEtaPhiM(pi_PT,pi_ETA,pi_PHI,pionmass);

    p_beta  = (-proton.P()+kaon.P()+pion.P())/(proton.P()+kaon.P()+pion.P());
    K_beta  = ( proton.P()-kaon.P()+pion.P())/(proton.P()+kaon.P()+pion.P());
    pi_beta = ( proton.P()+kaon.P()-pion.P())/(proton.P()+kaon.P()+pion.P());

    TLorentzVector p_as_pi;
    p_as_pi.SetVectM(proton.Vect(),pionmass);
    TLorentzVector p_as_K;
    p_as_K.SetVectM(proton.Vect(),kaonmass);

    TLorentzVector K_as_pi;
    K_as_pi.SetVectM(kaon.Vect(),pionmass);
    TLorentzVector K_as_p;
    K_as_p.SetVectM(kaon.Vect(),protonmass);

    TLorentzVector pi_as_K;
    pi_as_K.SetVectM(pion.Vect(),kaonmass);
    TLorentzVector pi_as_p;
    pi_as_p.SetVectM(pion.Vect(),protonmass);

    p_as_piKpi_M = (p_as_pi + kaon + pion).M();
    p_as_KKpi_M = (p_as_K + kaon + pion).M();

    pK_as_pipi_M = (proton + K_as_pi + pion).M();
    pK_as_ppi_M = (proton + K_as_p + pion).M();

    pKpi_as_K_M = (proton + kaon + pi_as_K).M();
    pKpi_as_p_M = (proton + kaon + pi_as_p).M();

    added_Xic_tree.Fill();

  }

  Xic_tree->SetDirectory(0);
  added_Xic_tree.Write();

  fSLBS->cd();
  TTree *Xic0_tree = (TTree*)gDirectory->Get("Xib2Xic0MuNu/Xic02pKKpi/DecayTree");

  double p_P, SSK1_P, SSK2_P, pi_P;
  double SSK1_PT, SSK2_PT, SSK1_ETA, SSK2_ETA, SSK1_PHI, SSK2_PHI;

  Xic0_tree->SetBranchStatus("*",0); //disable all branches
  //now switch on the ones we need (saves a lot of time)
  Xic0_tree->SetBranchStatus("Xib_M",1);
  Xic0_tree->SetBranchStatus("Xib_PT",1);
  Xic0_tree->SetBranchStatus("Xib_ETA",1);
  Xic0_tree->SetBranchStatus("Xib_PHI",1);
  Xic0_tree->SetBranchStatus("Xib_OWNPV_X",1);
  Xic0_tree->SetBranchStatus("Xib_OWNPV_Y",1);
  Xic0_tree->SetBranchStatus("Xib_OWNPV_Z",1);
  Xic0_tree->SetBranchStatus("Xib_ENDVERTEX_X",1);
  Xic0_tree->SetBranchStatus("Xib_ENDVERTEX_Y",1);
  Xic0_tree->SetBranchStatus("Xib_ENDVERTEX_Z",1);

  Xic0_tree->SetBranchStatus("Xic_M",1);
  Xic0_tree->SetBranchStatus("Xic_PT",1);
  Xic0_tree->SetBranchStatus("Xic_ETA",1);
  Xic0_tree->SetBranchStatus("Xic_PHI",1);

  Xic0_tree->SetBranchStatus("Added_n_Particles",1);
  Xic0_tree->SetBranchStatus("Added_H_PT",1);
  Xic0_tree->SetBranchStatus("Added_H_ETA",1);
  Xic0_tree->SetBranchStatus("Added_H_PHI",1);

  Xic0_tree->SetBranchStatus("p_P",1);
  Xic0_tree->SetBranchStatus("SSK1_P",1);
  Xic0_tree->SetBranchStatus("SSK2_P",1);
  Xic0_tree->SetBranchStatus("pi_P",1);

  Xic0_tree->SetBranchStatus("p_PT",1);
  Xic0_tree->SetBranchStatus("p_ETA",1);
  Xic0_tree->SetBranchStatus("p_PHI",1);
  Xic0_tree->SetBranchStatus("SSK1_PT",1);
  Xic0_tree->SetBranchStatus("SSK1_ETA",1);
  Xic0_tree->SetBranchStatus("SSK1_PHI",1);
  Xic0_tree->SetBranchStatus("SSK2_PT",1);
  Xic0_tree->SetBranchStatus("SSK2_ETA",1);
  Xic0_tree->SetBranchStatus("SSK2_PHI",1);
  Xic0_tree->SetBranchStatus("pi_PT",1);
  Xic0_tree->SetBranchStatus("pi_ETA",1);
  Xic0_tree->SetBranchStatus("pi_PHI",1);

  //set the branch addresses
  Xic0_tree->SetBranchAddress("Xib_M",&Xb_M);
  Xic0_tree->SetBranchAddress("Xib_PT",&Xb_PT);
  Xic0_tree->SetBranchAddress("Xib_ETA",&Xb_ETA);
  Xic0_tree->SetBranchAddress("Xib_PHI",&Xb_PHI);
  Xic0_tree->SetBranchAddress("Xib_OWNPV_X",&Xb_OWNPV_X);
  Xic0_tree->SetBranchAddress("Xib_OWNPV_Y",&Xb_OWNPV_Y);
  Xic0_tree->SetBranchAddress("Xib_OWNPV_Z",&Xb_OWNPV_Z);
  Xic0_tree->SetBranchAddress("Xib_ENDVERTEX_X",&Xb_ENDVERTEX_X);
  Xic0_tree->SetBranchAddress("Xib_ENDVERTEX_Y",&Xb_ENDVERTEX_Y);
  Xic0_tree->SetBranchAddress("Xib_ENDVERTEX_Z",&Xb_ENDVERTEX_Z);

  Xic0_tree->SetBranchAddress("Xic_M",&Xc_M);
  Xic0_tree->SetBranchAddress("Xic_PT",&Xc_PT);
  Xic0_tree->SetBranchAddress("Xic_ETA",&Xc_ETA);
  Xic0_tree->SetBranchAddress("Xic_PHI",&Xc_PHI);

  Xic0_tree->SetBranchAddress("Added_n_Particles",&Added_n_Particles);
  Xic0_tree->SetBranchAddress("Added_H_PT",&Added_H_PT);
  Xic0_tree->SetBranchAddress("Added_H_ETA",&Added_H_ETA);
  Xic0_tree->SetBranchAddress("Added_H_PHI",&Added_H_PHI);

  Xic0_tree->SetBranchAddress("p_P",&p_P);
  Xic0_tree->SetBranchAddress("SSK1_P",&SSK1_P);
  Xic0_tree->SetBranchAddress("SSK2_P",&SSK2_P);
  Xic0_tree->SetBranchAddress("pi_P",&pi_P);

  Xic0_tree->SetBranchAddress("p_PT",&p_PT);
  Xic0_tree->SetBranchAddress("SSK1_PT",&SSK1_PT);
  Xic0_tree->SetBranchAddress("SSK2_PT",&SSK2_PT);
  Xic0_tree->SetBranchAddress("pi_PT",&pi_PT);
  Xic0_tree->SetBranchAddress("p_ETA",&p_ETA);
  Xic0_tree->SetBranchAddress("SSK1_ETA",&SSK1_ETA);
  Xic0_tree->SetBranchAddress("SSK2_ETA",&SSK2_ETA);
  Xic0_tree->SetBranchAddress("pi_ETA",&pi_ETA);
  Xic0_tree->SetBranchAddress("p_PHI",&p_PHI);
  Xic0_tree->SetBranchAddress("SSK1_PHI",&SSK1_PHI);
  Xic0_tree->SetBranchAddress("SSK2_PHI",&SSK2_PHI);
  Xic0_tree->SetBranchAddress("pi_PHI",&pi_PHI);


  double SSK1_beta, SSK2_beta;

  f1->cd();
  //f1->mkdir("Xib2Xic0MuNu/Xic02pKKpi");
  //f1->cd("Xib2Xic0MuNu/Xic02pKKpi");
  TTree added_Xic0_tree("Xic02pKKpi","Xic02pKKpi");

  added_Xic0_tree.Branch("Xib_CorrM", &Xb_CorrM, "Xib_CorrM/D");
  added_Xic0_tree.Branch("p_beta", &p_beta, "p_beta/D");
  added_Xic0_tree.Branch("SSK1_beta", &SSK1_beta, "SSK1_beta/D");
  added_Xic0_tree.Branch("SSK2_beta", &SSK2_beta, "SSK2_beta/D");
  added_Xic0_tree.Branch("pi_beta", &pi_beta, "pi_beta/D");
  added_Xic0_tree.Branch("Added_n_Particles", &Added_n_Particles, "Added_n_Particles/I");
  added_Xic0_tree.Branch("Xcpi_CosTheta", &Xcpi_CosTheta, "Xcpi_CosTheta[Added_n_Particles]/F");
  added_Xic0_tree.Branch("XcK_CosTheta", &XcK_CosTheta, "XcK_CosTheta[Added_n_Particles]/F");
  added_Xic0_tree.Branch("Xcp_CosTheta", &Xcp_CosTheta, "Xcp_CosTheta[Added_n_Particles]/F");
  added_Xic0_tree.Branch("p_as_piKKpi_M", &p_as_piKpi_M, "p_as_piKKpi_M/D");
  added_Xic0_tree.Branch("p_as_KKKpi_M", &p_as_KKpi_M, "p_as_KKKpi_M/D");

  UInt_t Xic0_nevents = Xic0_tree->GetEntries();
  cout << "Entries in Xic0 tree: " << Xic0_nevents << endl;

  for (UInt_t evt = 0; evt < Xic0_nevents;evt++) {
    Xic0_tree->GetEntry(evt);

    TVector3 dir(Xb_ENDVERTEX_X-Xb_OWNPV_X,Xb_ENDVERTEX_Y-Xb_OWNPV_Y,Xb_ENDVERTEX_Z-Xb_OWNPV_Z);
    TVector3 mom;
    mom.SetPtEtaPhi(Xb_PT,Xb_ETA,Xb_PHI);
    double dmag2 = dir.Mag2();
    double ptprime = 0;
    if ( 0 == dmag2 ) ptprime = mom.Mag();
    else ptprime = (mom - dir * ( mom.Dot( dir ) / dmag2 )).Mag() ;
    Xb_CorrM = sqrt(Xb_M*Xb_M + ptprime*ptprime) + ptprime;

    TLorentzVector Xb;
    Xb.SetPtEtaPhiM(Xb_PT,Xb_ETA,Xb_PHI,Xb_CorrM);
    TLorentzVector Xc;
    Xc.SetPtEtaPhiM(Xc_PT,Xc_ETA,Xc_PHI,Xc_M);
    for(int i = 0; i < Added_n_Particles; i++){
      TLorentzVector Hpi;
      Hpi.SetPtEtaPhiM(Added_H_PT[i],Added_H_ETA[i],Added_H_PHI[i],pionmass);
      TLorentzVector HK;
      HK.SetPtEtaPhiM(Added_H_PT[i],Added_H_ETA[i],Added_H_PHI[i],kaonmass);
      TLorentzVector Hp;
      Hp.SetPtEtaPhiM(Added_H_PT[i],Added_H_ETA[i],Added_H_PHI[i],protonmass);
      TLorentzVector Xcpi = Hpi + Xc;
      TLorentzVector XcK = HK + Xc;
      TLorentzVector Xcp = Hp + Xc;
      Xcpi.Boost(-Xb.BoostVector());
      Xcpi_CosTheta[i] = cos(Xcpi.Angle(Xb.Vect()));
      XcK.Boost(-Xb.BoostVector());
      XcK_CosTheta[i] = cos(XcK.Angle(Xb.Vect()));
      Xcp.Boost(-Xb.BoostVector());
      Xcp_CosTheta[i] = cos(Xcp.Angle(Xb.Vect()));
    }
    p_beta    = (-p_P+SSK1_P+SSK2_P+pi_P)/(p_P+SSK1_P+SSK2_P+pi_P);
    SSK1_beta = ( p_P-SSK1_P+SSK2_P+pi_P)/(p_P+SSK1_P+SSK2_P+pi_P);
    SSK2_beta = ( p_P+SSK1_P-SSK2_P+pi_P)/(p_P+SSK1_P+SSK2_P+pi_P);
    pi_beta   = ( p_P+SSK1_P+SSK2_P-pi_P)/(p_P+SSK1_P+SSK2_P+pi_P);

    TLorentzVector proton;
    proton.SetPtEtaPhiM(p_PT,p_ETA,p_PHI,protonmass);
    TLorentzVector kaon1;
    kaon1.SetPtEtaPhiM(SSK1_PT,SSK1_ETA,SSK1_PHI,kaonmass);
    TLorentzVector kaon2;
    kaon2.SetPtEtaPhiM(SSK2_PT,SSK2_ETA,SSK2_PHI,kaonmass);
    TLorentzVector pion;
    pion.SetPtEtaPhiM(pi_PT,pi_ETA,pi_PHI,pionmass);

    TLorentzVector p_as_pi;
    p_as_pi.SetVectM(proton.Vect(),pionmass);
    TLorentzVector p_as_K;
    p_as_K.SetVectM(proton.Vect(),kaonmass);

    p_as_piKpi_M = (p_as_pi + kaon1 + kaon2 + pion).M();
    p_as_KKpi_M = (p_as_K + kaon1 + kaon2 + pion).M();

    added_Xic0_tree.Fill();

  }

  added_Xic0_tree.Write();

  fSLBS->cd();
  TTree *Omegac_tree = (TTree*)gDirectory->Get("Omegab2Omegac0MuNu/Omegac2pKKpi/DecayTree");

  Omegac_tree->SetBranchStatus("*",0); //disable all branches
  //now switch on the ones we need (saves a lot of time)
  Omegac_tree->SetBranchStatus("Omegab_M",1);
  Omegac_tree->SetBranchStatus("Omegab_PT",1);
  Omegac_tree->SetBranchStatus("Omegab_ETA",1);
  Omegac_tree->SetBranchStatus("Omegab_PHI",1);
  Omegac_tree->SetBranchStatus("Omegab_OWNPV_X",1);
  Omegac_tree->SetBranchStatus("Omegab_OWNPV_Y",1);
  Omegac_tree->SetBranchStatus("Omegab_OWNPV_Z",1);
  Omegac_tree->SetBranchStatus("Omegab_ENDVERTEX_X",1);
  Omegac_tree->SetBranchStatus("Omegab_ENDVERTEX_Y",1);
  Omegac_tree->SetBranchStatus("Omegab_ENDVERTEX_Z",1);

  Omegac_tree->SetBranchStatus("Omegac_M",1);
  Omegac_tree->SetBranchStatus("Omegac_PT",1);
  Omegac_tree->SetBranchStatus("Omegac_ETA",1);
  Omegac_tree->SetBranchStatus("Omegac_PHI",1);

  Omegac_tree->SetBranchStatus("Added_n_Particles",1);
  Omegac_tree->SetBranchStatus("Added_H_PT",1);
  Omegac_tree->SetBranchStatus("Added_H_ETA",1);
  Omegac_tree->SetBranchStatus("Added_H_PHI",1);

  Omegac_tree->SetBranchStatus("p_P",1);
  Omegac_tree->SetBranchStatus("SSK1_P",1);
  Omegac_tree->SetBranchStatus("SSK2_P",1);
  Omegac_tree->SetBranchStatus("pi_P",1);

  //set the branch addresses
  Omegac_tree->SetBranchAddress("Omegab_M",&Xb_M);
  Omegac_tree->SetBranchAddress("Omegab_PT",&Xb_PT);
  Omegac_tree->SetBranchAddress("Omegab_ETA",&Xb_ETA);
  Omegac_tree->SetBranchAddress("Omegab_PHI",&Xb_PHI);
  Omegac_tree->SetBranchAddress("Omegab_OWNPV_X",&Xb_OWNPV_X);
  Omegac_tree->SetBranchAddress("Omegab_OWNPV_Y",&Xb_OWNPV_Y);
  Omegac_tree->SetBranchAddress("Omegab_OWNPV_Z",&Xb_OWNPV_Z);
  Omegac_tree->SetBranchAddress("Omegab_ENDVERTEX_X",&Xb_ENDVERTEX_X);
  Omegac_tree->SetBranchAddress("Omegab_ENDVERTEX_Y",&Xb_ENDVERTEX_Y);
  Omegac_tree->SetBranchAddress("Omegab_ENDVERTEX_Z",&Xb_ENDVERTEX_Z);

  Omegac_tree->SetBranchAddress("Omegac_M",&Xc_M);
  Omegac_tree->SetBranchAddress("Omegac_PT",&Xc_PT);
  Omegac_tree->SetBranchAddress("Omegac_ETA",&Xc_ETA);
  Omegac_tree->SetBranchAddress("Omegac_PHI",&Xc_PHI);

  Omegac_tree->SetBranchAddress("Added_n_Particles",&Added_n_Particles);
  Omegac_tree->SetBranchAddress("Added_H_PT",&Added_H_PT);
  Omegac_tree->SetBranchAddress("Added_H_ETA",&Added_H_ETA);
  Omegac_tree->SetBranchAddress("Added_H_PHI",&Added_H_PHI);

  Omegac_tree->SetBranchAddress("p_P",&p_P);
  Omegac_tree->SetBranchAddress("SSK1_P",&SSK1_P);
  Omegac_tree->SetBranchAddress("SSK2_P",&SSK2_P);
  Omegac_tree->SetBranchAddress("pi_P",&pi_P);

  f1->cd();
  //f1->mkdir("Omegab2Omegac0MuNu/Omegac2pKKpi");
  //f1->cd("Omegab2Omegac0MuNu/Omegac2pKKpi");
  TTree added_Omegac_tree("Omegac2pKKpi","Omegac2pKKpi");

  added_Omegac_tree.Branch("Omegab_CorrM", &Xb_CorrM, "Omegab_CorrM/D");
  added_Omegac_tree.Branch("p_beta", &p_beta, "p_beta/D");
  added_Omegac_tree.Branch("SSK1_beta", &SSK1_beta, "SSK1_beta/D");
  added_Omegac_tree.Branch("SSK2_beta", &SSK2_beta, "SSK2_beta/D");
  added_Omegac_tree.Branch("pi_beta", &pi_beta, "pi_beta/D");
  added_Omegac_tree.Branch("Added_n_Particles", &Added_n_Particles, "Added_n_Particles/I");
  added_Omegac_tree.Branch("Xcpi_CosTheta", &Xcpi_CosTheta, "Xcpi_CosTheta[Added_n_Particles]/F");
  added_Omegac_tree.Branch("XcK_CosTheta", &XcK_CosTheta, "XcK_CosTheta[Added_n_Particles]/F");
  added_Omegac_tree.Branch("Xcp_CosTheta", &Xcp_CosTheta, "Xcp_CosTheta[Added_n_Particles]/F");

  UInt_t Omegac_nevents = Omegac_tree->GetEntries();
  cout << "Entries in Omegac tree: " << Omegac_nevents << endl;

  for (UInt_t evt = 0; evt < Omegac_nevents;evt++) {
    Omegac_tree->GetEntry(evt);

    TVector3 dir(Xb_ENDVERTEX_X-Xb_OWNPV_X,Xb_ENDVERTEX_Y-Xb_OWNPV_Y,Xb_ENDVERTEX_Z-Xb_OWNPV_Z);
    TVector3 mom;
    mom.SetPtEtaPhi(Xb_PT,Xb_ETA,Xb_PHI);
    double dmag2 = dir.Mag2();
    double ptprime = 0;
    if ( 0 == dmag2 ) ptprime = mom.Mag();
    else ptprime = (mom - dir * ( mom.Dot( dir ) / dmag2 )).Mag() ;
    Xb_CorrM = sqrt(Xb_M*Xb_M + ptprime*ptprime) + ptprime;

    TLorentzVector Xb;
    Xb.SetPtEtaPhiM(Xb_PT,Xb_ETA,Xb_PHI,Xb_CorrM);
    TLorentzVector Xc;
    Xc.SetPtEtaPhiM(Xc_PT,Xc_ETA,Xc_PHI,Xc_M);
    for(int i = 0; i < Added_n_Particles; i++){
      TLorentzVector Hpi;
      Hpi.SetPtEtaPhiM(Added_H_PT[i],Added_H_ETA[i],Added_H_PHI[i],pionmass);
      TLorentzVector HK;
      HK.SetPtEtaPhiM(Added_H_PT[i],Added_H_ETA[i],Added_H_PHI[i],kaonmass);
      TLorentzVector Hp;
      Hp.SetPtEtaPhiM(Added_H_PT[i],Added_H_ETA[i],Added_H_PHI[i],protonmass);
      TLorentzVector Xcpi = Hpi + Xc;
      TLorentzVector XcK = HK + Xc;
      TLorentzVector Xcp = Hp + Xc;
      Xcpi.Boost(-Xb.BoostVector());
      Xcpi_CosTheta[i] = cos(Xcpi.Angle(Xb.Vect()));
      XcK.Boost(-Xb.BoostVector());
      XcK_CosTheta[i] = cos(XcK.Angle(Xb.Vect()));
      Xcp.Boost(-Xb.BoostVector());
      Xcp_CosTheta[i] = cos(Xcp.Angle(Xb.Vect()));
    }
    p_beta    = (-p_P+SSK1_P+SSK2_P+pi_P)/(p_P+SSK1_P+SSK2_P+pi_P);
    SSK1_beta = ( p_P-SSK1_P+SSK2_P+pi_P)/(p_P+SSK1_P+SSK2_P+pi_P);
    SSK2_beta = ( p_P+SSK1_P-SSK2_P+pi_P)/(p_P+SSK1_P+SSK2_P+pi_P);
    pi_beta   = ( p_P+SSK1_P+SSK2_P-pi_P)/(p_P+SSK1_P+SSK2_P+pi_P);

    added_Omegac_tree.Fill();

  }

  added_Omegac_tree.Write();

  clock->Stop();clock->Print();delete clock;
  return;
}
Exemple #22
0
void polGen(double rapdilepton_min = 1,
		double rapdilepton_max = 1,
		double pTdilepton_min = 1,
		double pTdilepton_max = 1,
		double mass_signal_peak  =  1,
		double mass_signal_sigma =  1,
		double n_sigmas_signal = 1,
		int n_events = 50000,
		double f_BG = 0.5,
		double lambda_theta_sig=1,
		double lambda_phi_sig=1,
		double lambda_thetaphi_sig=1,
		double lambda_theta_bkg=1,
		double lambda_phi_bkg=1,
		double lambda_thetaphi_bkg=1,
		int frameSig=1,//CS...1, HX...2, PX...3
		int frameBkg=1,//CS...1, HX...2, PX...3
		int nGen=1,
		Char_t *dirstruct = "ToyDirectory_Default"
){

	char frameSigName[200];
	if(frameSig==1)sprintf(frameSigName,"CS");
	if(frameSig==2)sprintf(frameSigName,"HX");
	if(frameSig==3)sprintf(frameSigName,"PX");
	char frameBkgName[200];
	if(frameBkg==1)sprintf(frameBkgName,"CS");
	if(frameBkg==2)sprintf(frameBkgName,"HX");
	if(frameBkg==3)sprintf(frameBkgName,"PX");


	if(frameSig==2) HX_is_natural_sig=true; if(frameSig==3) PX_is_natural_sig=true; //else CS is the natural frame by default
	if(frameBkg==2) HX_is_natural_bkg=true; if(frameBkg==3) PX_is_natural_bkg=true; //else CS is the natural frame by default

	cout<<"Number of Events to be generated ........... "<<n_events<<endl;
	cout<<"pT min ..................................... "<<pTdilepton_min<<endl;
	cout<<"pT max ..................................... "<<pTdilepton_max<<endl;
	cout<<"Rapidity min ............................... "<<rapdilepton_min<<endl;
	cout<<"Rapidity max ............................... "<<rapdilepton_max<<endl;
	cout<<"Background Fraction ........................ "<<f_BG<<endl;
	cout<<"Injected lambda_theta Signal ............... "<<lambda_theta_sig<<" , in the "<<frameSigName<<" frame"<<endl;
	cout<<"Injected lambda_phi Signal ................. "<<lambda_phi_sig<<" , in the "<<frameSigName<<" frame"<<endl;
	cout<<"Injected lambda_thetaphi Signal ............ "<<lambda_thetaphi_sig<<" , in the "<<frameSigName<<" frame"<<endl;
	cout<<"Injected lambda_theta Background............ "<<lambda_theta_bkg<<" , in the "<<frameBkgName<<" frame"<<endl;
	cout<<"Injected lambda_phi Background ............. "<<lambda_phi_bkg<<" , in the "<<frameBkgName<<" frame"<<endl;
	cout<<"Injected lambda_thetaphi Background ........ "<<lambda_thetaphi_bkg<<" , in the "<<frameBkgName<<" frame"<<endl;
	cout<<"Number of Generation ....................... "<<nGen<<endl;
	cout<<"Directory Structure of Output .............. "<<dirstruct<<endl;


	double mass_min = mass_signal_peak - n_sigmas_signal*mass_signal_sigma;
	double mass_max = mass_signal_peak + n_sigmas_signal*mass_signal_sigma;

	char outfilename [500];
	sprintf(outfilename,"%s/genData.root",dirstruct);

  gROOT->Reset();

  delete gRandom;
  gRandom = new TRandom3(0);

  TF1* pT_distr = new TF1("pT_distr",func_pT_gen,pTdilepton_min,pTdilepton_max,0);
  TF1* rap_distr = new TF1("rap_distr",func_rap_gen,rapdilepton_min,rapdilepton_max,0);

  TFile* hfileout = new TFile(outfilename, "RECREATE", "genData");
  TTree* genData = new TTree("genData","genData");

  // Structure of output ntuple

  TLorentzVector* lepP = new TLorentzVector(0.,0.,0.,0.);
  genData->Branch("lepP","TLorentzVector",&lepP);
  TLorentzVector* lepN = new TLorentzVector(0.,0.,0.,0.);
  genData->Branch("lepN","TLorentzVector",&lepN);

  double costh_CS;  genData->Branch("costh_CS",     &costh_CS,     "costh_CS/D");
  double phi_CS;    genData->Branch("phi_CS",       &phi_CS,       "phi_CS/D"  );
  double phith_CS;  genData->Branch("phith_CS",     &phith_CS,     "phith_CS/D");

  double costh_HX;  genData->Branch("costh_HX",     &costh_HX,     "costh_HX/D");
  double phi_HX;    genData->Branch("phi_HX",       &phi_HX,       "phi_HX/D"  );
  double phith_HX;  genData->Branch("phith_HX",     &phith_HX,     "phith_HX/D");

  double costh_PX;  genData->Branch("costh_PX",     &costh_PX,     "costh_PX/D");
  double phi_PX;    genData->Branch("phi_PX",       &phi_PX,       "phi_PX/D"  );
  double phith_PX;  genData->Branch("phith_PX",     &phith_PX,     "phith_PX/D");

  double cosalpha;  genData->Branch("cosalpha",     &cosalpha,     "cosalpha/D");

  double pT;        genData->Branch("pT",           &pT,           "pT/D"  );
  double rap;       genData->Branch("rap",          &rap,          "rap/D" );
  double mass;      genData->Branch("mass",         &mass,         "mass/D");

  double deltaHXCS; genData->Branch("deltaHXCS",    &deltaHXCS,    "deltaHXCS/D");

  int isBG;         genData->Branch("isBG",         &isBG,         "isBG/I");


  // extremes and binning of lambda_gen extraction histos
  const double l_min = -1;
  const double l_max =  1;
  const double l_step_1D = 0.02;


  TH1D* h_costh2_CS = new TH1D( "h_costh2_CS", "", int((l_max-l_min)/l_step_1D), l_min, l_max );
  TH1D* h_cos2ph_CS = new TH1D( "h_cos2ph_CS", "", int((l_max-l_min)/l_step_1D), l_min, l_max );
  TH1D* h_sin2thcosph_CS = new TH1D( "h_sin2thcosph_CS", "", int((l_max-l_min)/l_step_1D), l_min, l_max );

  TH1D* h_costh2_HX = new TH1D( "h_costh2_HX", "", int((l_max-l_min)/l_step_1D), l_min, l_max );
  TH1D* h_cos2ph_HX = new TH1D( "h_cos2ph_HX", "", int((l_max-l_min)/l_step_1D), l_min, l_max );
  TH1D* h_sin2thcosph_HX = new TH1D( "h_sin2thcosph_HX", "", int((l_max-l_min)/l_step_1D), l_min, l_max );

  TH1D* h_costh2_PX = new TH1D( "h_costh2_PX", "", int((l_max-l_min)/l_step_1D), l_min, l_max );
  TH1D* h_cos2ph_PX = new TH1D( "h_cos2ph_PX", "", int((l_max-l_min)/l_step_1D), l_min, l_max );
  TH1D* h_sin2thcosph_PX = new TH1D( "h_sin2thcosph_PX", "", int((l_max-l_min)/l_step_1D), l_min, l_max );

  double costh2;
  double cos2ph;
  double sin2thcosph;
  double Phi;

  const int n_step = n_events/5;
  int n_step_=1;


  cout << endl;
  cout << "Generating " << n_events << " dilepton events"<< endl;
  cout << "------------------------------------------------------------" << endl;
  cout << "Progress: "<<endl;



/////////////////// CYCLE OF EVENTS ////////////////////////
  for(int i_event = 1; i_event <= n_events; i_event++){

	    if (i_event%n_step == 0) {cout << n_step_*20 <<" % "<<endl; n_step_++;}

	    // generation of dilepton in the pp event in the pp CM

    // mass

    isBG = 0;

    if ( gRandom->Uniform() < f_BG ) { mass = gRandom->Uniform(mass_min, mass_max); isBG = 1; }
                                        else { do { mass = gRandom->Gaus(mass_signal_peak, mass_signal_sigma); }
                                               while ( mass < mass_min || mass > mass_max ); }

    // pT:

    pT = pT_distr->GetRandom();

    // pL:

    double rap_sign = gRandom->Uniform(-1., 1.); rap_sign /= TMath::Abs(rap_sign);
    rap = rap_distr->GetRandom() * rap_sign;
    double mT = sqrt( mass*mass + pT*pT );
    double pL1 = 0.5 *mT * exp(rap);
    double pL2 = - 0.5 *mT * exp(-rap);
    double pL = pL1 + pL2;

    // Phi:

    double Phi = 2. * gPI * gRandom->Uniform(1.);

    // 4-vector:

    TLorentzVector dilepton;
    dilepton.SetXYZM( pT * cos(Phi) , pT * sin(Phi), pL, mass );


    // generation of polarization (generic reference frame)

    double lambda_theta    = lambda_theta_sig;
    double lambda_phi      = lambda_phi_sig;
    double lambda_thetaphi = lambda_thetaphi_sig;
    bool HX_is_natural = HX_is_natural_sig;
    bool PX_is_natural = PX_is_natural_sig;

    if ( isBG ) {
       lambda_theta    = lambda_theta_bkg;
       lambda_phi      = lambda_phi_bkg;
       lambda_thetaphi = lambda_thetaphi_bkg;
       HX_is_natural = HX_is_natural_bkg;
       PX_is_natural = PX_is_natural_bkg;
    }


    double costhphidistr_max = 1. + TMath::Abs(lambda_phi) + TMath::Abs(lambda_thetaphi);
    double costhphidistr_rnd;
    double costhphidistr;
    double costh_gen;
    double sinth_gen;
    double phi_gen;

    if ( lambda_theta > 0. ) costhphidistr_max += lambda_theta;

    do { costh_gen = -1. + 2. * gRandom->Uniform(1.);
         phi_gen   = 2. * gPI * gRandom->Uniform(1.);
         sinth_gen = sqrt( 1. - costh_gen*costh_gen );
         costhphidistr_rnd = costhphidistr_max * gRandom->Uniform(1.);
         costhphidistr = 1. + lambda_theta    * costh_gen*costh_gen
                            + lambda_phi      * sinth_gen*sinth_gen * cos(2.*phi_gen)
                            + lambda_thetaphi * 2.* sinth_gen*costh_gen * cos(phi_gen);
       } while ( costhphidistr_rnd > costhphidistr );


    // lepton momentum in the dilepton rest frame:

    double p_lepton_DILEP = sqrt( 0.25*mass*mass - Mlepton*Mlepton );

    TLorentzVector lepton_DILEP;

    lepton_DILEP.SetXYZM( p_lepton_DILEP * sinth_gen * cos(phi_gen),
                          p_lepton_DILEP * sinth_gen * sin(phi_gen),
                          p_lepton_DILEP * costh_gen,
                          Mlepton );


    // reference directions to calculate angles:

    TVector3 lab_to_dilep = -dilepton.BoostVector();

    TLorentzVector beam1_DILEP = beam1_LAB;
    beam1_DILEP.Boost(lab_to_dilep);         // beam1 in the dilepton rest frame
    TLorentzVector beam2_DILEP = beam2_LAB;
    beam2_DILEP.Boost(lab_to_dilep);         // beam2 in the dilepton rest frame

    TVector3 beam1_direction     = beam1_DILEP.Vect().Unit();
    TVector3 beam2_direction     = beam2_DILEP.Vect().Unit();
    TVector3 dilep_direction     = dilepton.Vect().Unit();
    TVector3 beam1_beam2_bisect  = ( beam1_direction - beam2_direction ).Unit();


    deltaHXCS = dilep_direction.Angle(beam1_beam2_bisect) * 180./gPI;

    // all polarization frames have the same Y axis = the normal to the plane formed by
    // the directions of the colliding hadrons

    TVector3 Yaxis = ( beam1_direction.Cross( beam2_direction ) ).Unit();

    // flip of y axis with rapidity

    if ( rap < 0 ) Yaxis = - Yaxis;

    TVector3 perpendicular_to_beam = ( beam1_beam2_bisect.Cross( Yaxis ) ).Unit();


    // step 1: transform (rotation) lepton momentum components from generation frame
    // to the frame with x,y,z axes as in the laboratory

    TVector3 oldZaxis = beam1_beam2_bisect;
    if ( HX_is_natural ) oldZaxis = dilep_direction;
    if ( PX_is_natural ) oldZaxis = perpendicular_to_beam;

    TVector3 oldYaxis = Yaxis;
    TVector3 oldXaxis = oldYaxis.Cross(oldZaxis);

    TRotation rotation;
    rotation.RotateAxes(oldXaxis, oldYaxis, oldZaxis);
                     // transforms coordinates from the "old" frame to the "xyz" frame

    TLorentzVector lepton_DILEP_xyz = lepton_DILEP;

    lepton_DILEP_xyz.Transform(rotation);
                     // lepton_DILEP_xyz is the lepton in the dilepton rest frame
                     // wrt to the lab axes

    // lepton 4-vectors in the LAB frame:

    TVector3 dilep_to_lab = dilepton.BoostVector();

    *lepP = lepton_DILEP_xyz;
    lepP->Boost(dilep_to_lab);
    lepN->SetPxPyPzE(-lepton_DILEP_xyz.Px(),-lepton_DILEP_xyz.Py(),-lepton_DILEP_xyz.Pz(),lepton_DILEP_xyz.E());
    lepN->Boost(dilep_to_lab);


    /////////////////////////////////////////////////////////////////////
    // CS frame


    TVector3 newZaxis = beam1_beam2_bisect;
    TVector3 newYaxis = Yaxis;
    TVector3 newXaxis = newYaxis.Cross( newZaxis );

    rotation.SetToIdentity();
    rotation.RotateAxes( newXaxis, newYaxis, newZaxis );
    rotation.Invert();  // transforms coordinates from the "xyz" frame to the new frame

    TVector3 lepton_DILEP_rotated = lepton_DILEP_xyz.Vect();

    lepton_DILEP_rotated.Transform(rotation);

    costh_CS = lepton_DILEP_rotated.CosTheta();

    phi_CS = lepton_DILEP_rotated.Phi() * 180. / gPI;

    if ( costh_CS < 0. ) phith_CS = phi_CS - 135.;
    if ( costh_CS > 0. ) phith_CS = phi_CS - 45.;

    if ( phith_CS < -180. ) phith_CS = 360. + phith_CS;


    /////////////////////////////////////////////////////////////////////
    // HELICITY frame

    newZaxis = dilep_direction;
    newYaxis = Yaxis;
    newXaxis = newYaxis.Cross( newZaxis );

    rotation.SetToIdentity();
    rotation.RotateAxes( newXaxis, newYaxis, newZaxis );
    rotation.Invert();

    lepton_DILEP_rotated = lepton_DILEP_xyz.Vect();

    lepton_DILEP_rotated.Transform(rotation);

    costh_HX = lepton_DILEP_rotated.CosTheta();

    phi_HX = lepton_DILEP_rotated.Phi() * 180. / gPI;

    if ( costh_HX < 0. ) phith_HX = phi_HX - 135.;
    if ( costh_HX > 0. ) phith_HX = phi_HX - 45.;

    if ( phith_HX < -180. ) phith_HX = 360. + phith_HX;


    /////////////////////////////////////////////////////////////////////
    // PERPENDICULAR HELICITY frame

    newZaxis = perpendicular_to_beam;
    newYaxis = Yaxis;
    newXaxis = newYaxis.Cross( newZaxis );

    rotation.SetToIdentity();
    rotation.RotateAxes( newXaxis, newYaxis, newZaxis );
    rotation.Invert();

    lepton_DILEP_rotated = lepton_DILEP_xyz.Vect();

    lepton_DILEP_rotated.Transform(rotation);

    costh_PX = lepton_DILEP_rotated.CosTheta();

    phi_PX = lepton_DILEP_rotated.Phi() * 180. / gPI;

    if ( costh_PX < 0. ) phith_PX = phi_PX - 135.;
    if ( costh_PX > 0. ) phith_PX = phi_PX - 45.;

    if ( phith_PX < -180. ) phith_PX = 360. + phith_PX;


    /////////////////////////////////////////////////////////////////////
    // invariant polarization angle

    cosalpha = sqrt( 1. - pow(costh_PX, 2.) ) * sin( lepton_DILEP_rotated.Phi() );



////// Filling Histograms of costh2, cos2ph and sin2thcosph for the extraction of the actual generated polarization

    if ( !isBG ){
		costh2=pow(costh_CS,2.);
	    Phi = phi_CS/180. * gPI ;
	    cos2ph = cos(2.*Phi);
	    sin2thcosph= sin(2.*acos(costh_CS))*cos(Phi);
	    h_costh2_CS->Fill( costh2 );
	    h_cos2ph_CS->Fill( cos2ph );
	    h_sin2thcosph_CS->Fill( sin2thcosph );

	    costh2=pow(costh_HX,2.);
	    Phi = phi_HX/180. * gPI ;
	    cos2ph = cos(2.*Phi);
	    sin2thcosph= sin(2.*acos(costh_HX))*cos(Phi);
	    h_costh2_HX->Fill( costh2 );
	    h_cos2ph_HX->Fill( cos2ph );
	    h_sin2thcosph_HX->Fill( sin2thcosph );

	    costh2=pow(costh_PX,2.);
	    Phi = phi_PX/180. * gPI ;
	    cos2ph = cos(2.*Phi);
	    sin2thcosph= sin(2.*acos(costh_PX))*cos(Phi);
	    h_costh2_PX->Fill( costh2 );
	    h_cos2ph_PX->Fill( cos2ph );
	    h_sin2thcosph_PX->Fill( sin2thcosph );
    }


//  filling of the ntuple:

    genData->Fill();


  } // end of external loop (generated events)

  cout << endl;


  double lamth_CS;
  double lamph_CS;
  double lamtp_CS;
  costh2=h_costh2_CS->GetMean();
  lamth_CS = (1. - 3. * costh2 ) / ( costh2 - 3./5. );
  cos2ph=h_cos2ph_CS->GetMean();
  lamph_CS = cos2ph * (3. + lamth_CS);
  sin2thcosph=h_sin2thcosph_CS->GetMean();
  lamtp_CS = sin2thcosph * 5./4. * (3. + lamth_CS);

  double lamth_HX;
  double lamph_HX;
  double lamtp_HX;
  costh2=h_costh2_HX->GetMean();
  lamth_HX = (1. - 3. * costh2 ) / ( costh2 - 3./5. );
  cos2ph=h_cos2ph_HX->GetMean();
  lamph_HX = cos2ph * (3. + lamth_HX);
  sin2thcosph=h_sin2thcosph_HX->GetMean();
  lamtp_HX = sin2thcosph * 5./4. * (3. + lamth_HX);

  double lamth_PX;
  double lamph_PX;
  double lamtp_PX;
  costh2=h_costh2_PX->GetMean();
  lamth_PX = (1. - 3. * costh2 ) / ( costh2 - 3./5. );
  cos2ph=h_cos2ph_PX->GetMean();
  lamph_PX = cos2ph * (3. + lamth_PX);
  sin2thcosph=h_sin2thcosph_PX->GetMean();
  lamtp_PX = sin2thcosph * 5./4. * (3. + lamth_PX);


  char resfilename[200];
  sprintf(resfilename,"%s/GenResults.root",dirstruct);
  TFile* GenResultFile = new TFile(resfilename, "RECREATE", "GenResultFile");

  TTree* GenResults = new TTree("GenResults","GenResults");
  GenResults->Branch("lthCS",         &lamth_CS,         "lthCS/D");
  GenResults->Branch("lphCS",         &lamph_CS,         "lphCS/D");
  GenResults->Branch("ltpCS",         &lamtp_CS,         "ltpCS/D");
  GenResults->Branch("lthHX",         &lamth_HX,         "lthHX/D");
  GenResults->Branch("lphHX",         &lamph_HX,         "lphHX/D");
  GenResults->Branch("ltpHX",         &lamtp_HX,         "ltpHX/D");
  GenResults->Branch("lthPX",         &lamth_PX,         "lthPX/D");
  GenResults->Branch("lphPX",         &lamph_PX,         "lphPX/D");
  GenResults->Branch("ltpPX",         &lamtp_PX,         "ltpPX/D");

  GenResults->Fill();


  GenResultFile->Write();
  GenResultFile->Close();

  hfileout->Write();
  hfileout->Close();

} // end of main
void gravitonPythia(){

  gStyle->SetOptStat(0);

  TreeReader data("pythia8_RS_WW.root");

  TH1F* h_cosTh = new TH1F("h_cosTh","RS Graviton by Pythia8",100,-1,1);
  h_cosTh->SetMinimum(0);
  h_cosTh->Sumw2();

  TH1F *h_cosThStar = (TH1F*)h_cosTh->Clone("h_cosThStar");
  
  for(Long64_t ev = 0 ; ev < data.GetEntriesFast(); ev++){

    data.GetEntry(ev);

    Int_t nGenPar = data.GetInt("nGenPar"); 
    Int_t* genParId = data.GetPtrInt("genParId");
    Int_t* genParSt = data.GetPtrInt("genParSt");
    Float_t* genParPt = data.GetPtrFloat("genParPt");
    Float_t* genParEta = data.GetPtrFloat("genParEta");
    Float_t* genParPhi = data.GetPtrFloat("genParPhi");
    Float_t* genParM = data.GetPtrFloat("genParM");


    // cos#theta_1 in the W rest frame
      
    Int_t chgLepID = -1;
    Int_t neuLepID = -1;

    TLorentzVector chgLep(0,0,0,0);
    TLorentzVector neuLep(0,0,0,0);

    for(Int_t i = 0; i < nGenPar; i++){

      if( genParSt[i] != 23 ) continue; 
      if( abs(genParId[i]) == 11 || abs(genParId[i]) == 13 || abs(genParId[i]) == 15 ) chgLepID = i;
      if( abs(genParId[i]) == 12 || abs(genParId[i]) == 14 || abs(genParId[i]) == 16 ) neuLepID = i;

    }

    chgLep.SetPtEtaPhiM(genParPt[chgLepID], 
			genParEta[chgLepID], 
			genParPhi[chgLepID], 
			genParM[chgLepID]);

    neuLep.SetPtEtaPhiM(genParPt[neuLepID], 
			genParEta[neuLepID], 
			genParPhi[neuLepID], 
			genParM[neuLepID]);

    TLorentzVector  Wb = chgLep + neuLep;

    TVector3 WbP = Wb.Vect();
    TVector3 bv = -Wb.BoostVector();

    chgLep.Boost(bv);
    
    TVector3 chgLepP = chgLep.Vect();
    
    Double_t cosTh = TMath::Cos(chgLepP.Angle(WbP));
   
    h_cosTh->Fill(cosTh);


    // cos#theta* in the RSG rest frame

    Int_t WplusID = -1;
    Int_t WminusID = -1;

    TLorentzVector Wplus(0,0,0,0);
    TLorentzVector Wminus(0,0,0,0);

    for(Int_t i = 0; i < nGenPar; i++){

      if( genParSt[i] !=  22 ) continue;
      if( genParId[i] == +24 ) WplusID = i;
      if( genParId[i] == -24 ) WminusID = i;

    }

    Wplus.SetPtEtaPhiM(genParPt[WplusID], 
		       genParEta[WplusID], 
		       genParPhi[WplusID], 
		       genParM[WplusID]);

    Wplus.SetPtEtaPhiM(genParPt[WminusID], 
		       genParEta[WminusID], 
		       genParPhi[WminusID], 
		       genParM[WminusID]);

    TLorentzVector RSG = Wplus + Wminus;

    TVector3 RSGP = RSG.Vect();
    TVector3 gv = -RSG.BoostVector();

    Wplus.Boost(gv);

    TVector3 WplusP = Wplus.Vect();

    Double_t cosThStar = TMath::Cos(WplusP.Angle(RSGP));

    h_cosThStar->Fill(cosThStar);

  }

  TCanvas* c[2];

  c[0] = new TCanvas("c0","",0,0,800,600);
  c[1] = new TCanvas("c1","",0,0,800,600);

  c[0]->cd(); 
  h_cosTh->SetXTitle("cos#theta_1 in the W rest frame");
  h_cosTh->Draw();

  c[1]->cd(); 
  h_cosThStar->SetXTitle("cos#theta* in the RSG rest frame");
  h_cosThStar->Draw();

  c[0]->Print("RSgravitonPythia.pdf(");
  c[1]->Print("RSgravitonPythia.pdf)");
    
}
Exemple #24
0
int xAna::HggTreeWriteLoop(const char* filename, int ijob, 
					  bool correctVertex, bool correctEnergy, 
					  bool setRho0
					  ) {

  //bool invDRtoTrk = false;


  if( _config == 0 ) {
    cout << " config file was not set properly... bail out" << endl;
    return -1;
  }

  if (fChain == 0) return -1;
  
  Long64_t nentries = fChain->GetEntriesFast();
  //  nentries = 10000;
  cout << "nentries: " << nentries << endl;  
  Long64_t entry_start = ijob    *_config->nEvtsPerJob();
  Long64_t entry_stop  = (ijob+1)*_config->nEvtsPerJob();
  if( _config->nEvtsPerJob() < 0 ) {
    entry_stop = nentries;
  }
  if( entry_stop  > nentries ) entry_stop = nentries;
  cout << "   *** doing entries from: " << entry_start << " -> " << entry_stop << endl;
  if( entry_start > entry_stop ) return -1;

  
  EnergyScaleReader enScaleSkimEOS; /// skim EOS bugged so need to undo the energy scale in the skim
  EnergyScaleReader enScale;
  //  enScaleSkimEOS.setup( "ecalCalibFiles/EnergyScale2012_Lisbon_9fb.txt" );
  enScale.setup( _config->energyScaleFile() );


  Float_t HiggsMCMass =  _weight_manager->getCrossSection()->getHiggsMass();
  Float_t HiggsMCPt   = -1;
  bool isHiggsSignal = false;
  if( HiggsMCMass > 0 ) isHiggsSignal = true;

  mode_ = _weight_manager->getCrossSection()->mode();
  isData = false;
  if(mode_==-1) isData = true;        

//  mode_ = ijob; //  

  DoCorrectVertex_ = correctVertex;
  DoCorrectEnergy_ = correctEnergy;
  DoSetRho0_ = setRho0;

  doJetRegression = _config->getDoJetRegression();
  doControlSample = _config->getDoControlSample();
  
  phoID_2011[0] = new TMVA::Reader("!Color:Silent");
  phoID_2011[1] = new TMVA::Reader("!Color:Silent");
  phoID_2012[0] = new TMVA::Reader("!Color:Silent");
  phoID_2012[1] = new TMVA::Reader("!Color:Silent");
  DiscriDiPho_2011 = new TMVA::Reader("!Color:Silent");
  DiscriDiPho_2012 = new TMVA::Reader("!Color:Silent");
  if(doJetRegression!=0) jetRegres = new TMVA::Reader("!Color:Silent");
  Setup_MVA();
  
  if( _config->setup() == "ReReco2011" )  for( int i = 0 ; i < 2; i++ ) phoID_mva[i] = phoID_2011[i];
  else                                    for( int i = 0 ; i < 2; i++ ) phoID_mva[i] = phoID_2012[i];

  MassResolution massResoCalc;
  massResoCalc.addSmearingTerm();
  if( _config->setup() == "ReReco2011" )  Ddipho_mva = DiscriDiPho_2011;
  else                                    Ddipho_mva = DiscriDiPho_2012;

  float Ddipho_cat[5]; Ddipho_cat[4] = -1; 
  if( _config->setup() == "ReReco2011" ) { Ddipho_cat[0] = 0.89; Ddipho_cat[1] = 0.72; Ddipho_cat[2] = 0.55; Ddipho_cat[3] = +0.05; }
  else                                   { Ddipho_cat[0] = 0.91; Ddipho_cat[1] = 0.79; Ddipho_cat[2] = 0.49; Ddipho_cat[3] = -0.05; }
  //  else                                   { Ddipho_cat[0] = 0.88; Ddipho_cat[1] = 0.71; Ddipho_cat[2] = 0.50; Ddipho_cat[3] = -0.05; }

  DiscriVBF_UseDiPhoPt = true;
  DiscriVBF_UsePhoPt   = true;
  DiscriVBF_cat.resize(2); DiscriVBF_cat[0] = 0.985; DiscriVBF_cat[1] = 0.93;
  DiscriVBF_useMvaSel  = _config->doVBFmvaCat();


  


  /// depending on the selection veto or not on electrons (can do muele, elemu,eleele)
  bool vetoElec[2] = {true,true};
  if( _config->invertElectronVeto() ) { vetoElec[0] = false; vetoElec[1] = false; }
  if( _config->isEleGamma()         ) { vetoElec[0] = false; vetoElec[1] = true ; }
  if( _config->isGammaEle()         ) { vetoElec[0] = true ; vetoElec[1] = false; }
  cout << " --------- veto electron config -----------" << endl;
  cout << " Leading  Pho VetoElec: " << vetoElec[0] << endl;
  cout << " Trailing Pho VetoElec: " << vetoElec[1] << endl;
  

  DoDebugEvent = true;
  
  bool DoPreselection = true;
  //  bool DoPrint = true;
  
  
  TString VertexFileNamePrefix;
  
  TRandom3 *rnd = new TRandom3();
  rnd->SetSeed(0);
  
  /// output tree and cross check file
   _xcheckTextFile.open(TString(filename)+".xcheck.txt");
   // _xcheckTextFile = cout;

  _minitree = new MiniTree( filename );
  TTree * tSkim = 0;
  if( _config->doSkimming() ) tSkim = (TTree*) fChain->CloneTree(0);

  InitHists();
  _minitree->mc_wXsec = _weight_manager->xSecW();
  _minitree->mc_wNgen = 100000./_weight_manager->getNevts();
  if( isData ) {
    _minitree->mc_wXsec = 1;
    _minitree->mc_wNgen = 1;
  }
    
  Int_t isprompt0 = -1;
  Int_t isprompt1 = -1;
  
  set<Long64_t> syncEvt;

  cout <<" ================ mode  "  << mode_   <<" ===============================  "<<endl;
  /// setupType has to be passed via config file
  //  photonOverSmearing overSmearICHEP("Test52_ichep");
  photonOverSmearing overSmearHCP( "oversmear_hcp2012" );
  photonOverSmearing overSmear(    _config->setup()    );
  int overSmearSyst = _config->getEnergyOverSmearingSyst();

  Long64_t nbytes = 0, nb = 0;
  ////////////////////////////////////////////////////////////////////////////
  //////////////////////////// Start the loop ////////////////////////////////
  ////////////////////////////////////////////////////////////////////////////
  vector<int>    nEvts;
  vector<string> nCutName;
  nCutName.push_back("TOTAL          :"); nEvts.push_back(0);
  nCutName.push_back("2 gammas       :"); nEvts.push_back(0);
  nCutName.push_back("triggers       :"); nEvts.push_back(0);
  nCutName.push_back("nan weight     :"); nEvts.push_back(0);
  nCutName.push_back("presel kin cuts:"); nEvts.push_back(0);
  nCutName.push_back("pass 2 gam incl:"); nEvts.push_back(0);
  nCutName.push_back("pass all       :"); nEvts.push_back(0);
  nCutName.push_back("   --> pass 2 gam lep: "); nEvts.push_back(0);
  nCutName.push_back("   --> pass 2 gam vbf: "); nEvts.push_back(0);

  vector<int> selVtxSumPt2(3);  selVtxSumPt2[0] = 0; selVtxSumPt2[1] = -1;   selVtxSumPt2[2] = -1;

  for (Long64_t jentry=entry_start; jentry< entry_stop ; ++jentry) {
    Long64_t ientry = LoadTree(jentry);

    if (ientry < -9999) break;
    if( jentry % 10000 == 0) cout<<"processing event "<<jentry<<endl;
    nb = fChain->GetEntry(jentry);   nbytes += nb;

    /// reset minitree variables
    _minitree->initEvent();

    // study mc truth block
    if( !isData ) {
      fillMCtruthInfo_HiggsSignal();
      _minitree->fillMCtrueOnly();
    }

    /// reco analysis
    unsigned icutlevel = 0;
    nEvts[icutlevel++]++;
    if( nPho < 2 ) continue; 
    nEvts[icutlevel++]++;
    
    /// set synchronisation flag
    if( syncEvt.find(event) != syncEvt.end() ) DoDebugEvent = true;
    else                                       DoDebugEvent = false;
    if( DoDebugEvent ) _xcheckTextFile << "==========================================================" << endl;
    if( DoDebugEvent ) _xcheckTextFile << "================= debugging event: " << event << endl;
    
    /// PU & BSz reweightings
    if( !isData ) {
      int itpu = 1;  /// 0 without OOT PU - 1 with OOT PU
      _minitree->mc_wPU  = _weight_manager->puW( nPU[itpu] );
     // PUwei  = _weight_manager->puWTrue( puTrue[itpu] );      
    }
    hTotEvents->Fill(1,_minitree->mc_wPU);


    
    bool sigWH = false ;
    bool sigZH = false ;    
    int  mc_whzh_type = 0;
    _minitree->mc_wHQT = 1;
    if( isHiggsSignal ) {
      if ( _weight_manager->getCrossSection()->getMCType() == "vh" ) 
      for( Int_t i=0; i < nMC && i <= 1; ++i ) { 
	  if( abs(mcPID[i]) == 24 ) sigWH=true;
	  if( abs(mcPID[i]) == 23 ) sigZH=true;
	}
      if( sigWH ) mc_whzh_type = 1;
      if( sigZH ) mc_whzh_type = 2;
      
      for( Int_t i=0; i<nMC; ++i)
      if ( abs(mcPID[i]) == 25 ) HiggsMCPt   = mcPt[i];

      if( _weight_manager->getCrossSection()->getMCType() == "ggh" && 
	  _config->setup().find( "ReReco2011" ) != string::npos )
	_minitree->mc_wHQT = getHqTWeight(HiggsMCMass, HiggsMCPt);      
    }
    


    
    if ((mode_ == 2 || mode_ ==1 ||  mode_ == 18 || mode_ == 19) && processID==18) continue;      
    
    // Remove double counting in gamma+jets and QCDjets
    
    Int_t mcIFSR_pho = 0;
    Int_t mcPartonic_pho = 0;
    if (mode_ == 1 || mode_ == 2 || mode_ == 3  ||  mode_ == 18 ||  mode_ == 19 ) {
      for (Int_t i=0; i<nMC; ++i) {    
	if (mcPID[i] == 22 && (fabs(mcMomPID[i]) < 6 || mcMomPID[i] == 21)) mcIFSR_pho++;
	if (mcPID[i] == 22 && mcMomPID[i] == 22) mcPartonic_pho++;
      }
    }
    
    // if pythia is used for diphoton.. no IFSR removing from QCD and Gjets!!!!!!      
    if ((mode_==1 || mode_ == 2  ||   mode_ == 18 ) && mcIFSR_pho >= 1 && mcPartonic_pho >=1) continue;
    if ((mode_ == 3 ||  mode_ == 19 )&& mcIFSR_pho == 2) continue;   

 
    bool prompt2= false;
    bool prompt1= false;
    bool prompt0= false;
    vertProb = -1;
    
    if (mode_ == 2  || mode_ == 1    ||   mode_ == 18     ){
      if      ( mcPartonic_pho >= 1 &&  mcIFSR_pho >= 1 ) prompt2 = true;
      else if ( mcPartonic_pho >= 1 &&  mcIFSR_pho == 0 ) prompt1 = true;
      else if ( mcPartonic_pho == 0 &&  mcIFSR_pho == 0 ) prompt0 = true;
    } else if(mode_ == 3 ||  mode_ == 19   ){
      if      ( mcIFSR_pho >= 2 ) prompt2 = true;
      else if ( mcIFSR_pho == 1 ) prompt1 = true;
      else if ( mcIFSR_pho == 0 ) prompt0 = true;
      if( prompt1 ) _minitree->mc_wXsec = 1.3*_weight_manager->xSecW();
    }
    
    if(mode_==1 || mode_==2 || mode_==3 || mode_==18 || mode_==19){
      if(prompt0)isprompt0=1;
      else isprompt0=0;
      if(prompt1)isprompt1=1;
      else isprompt1=0;
    }
    
    if( mode_ == 20 && isZgamma() ) continue;

    /// wei weight is just temporary and may not contain all info.
    float wei = _minitree->mc_wXsec * _minitree->mc_wPU  
      * _minitree->mc_wNgen * _minitree->mc_wHQT;

    if( isData && !PassTriggerSelection() ) continue;      nEvts[icutlevel++]++;
    if( std::isinf( wei ) || std::isnan( wei ) )continue;  nEvts[icutlevel++]++;
    
    
    
    //// ********************* define S4 variable **********************////
    for( int i=0; i<nPho; ++i){
      if( _config->setup() == "ReReco2011" ) phoS4ratio[i] = 1;
      else                                   phoS4ratio[i] = phoE2x2[i] / phoE5x5[i];
    }
    //// ************************************************************* ////

    if( !isData ) {
      //// ************** MC corrections (mostly MC) ******************* //// 
      // 1. energy shifting / smearing
      for( int i=0; i<nPho; ++i)
	if( fabs(phoSCEta[i]) <= 2.5 ) {
	  float smearing = overSmear.randOverSmearing(phoSCEta[i],phoR9[i],isInGAP_EB(i),overSmearSyst);
	  phoRegrE[i] *= (1 + smearing); 
	  phoE[i]     *= (1 + smearing); 
	  /// from MassFactorized in gglobe:   energyCorrectedError[ipho] *=(l.pho_isEB[ipho]) ? 1.07 : 1.045 ;
	  float smearFactor = 1;
	  if( _config->setup() == "ReReco2011" ) smearFactor = fabs(phoSCEta[i]) < 1.45 ? 1.07: 1.045;
	  phoRegrErr[i] *= smearFactor;
	}  
      
      
      // 2. reweighting of photon id variables (R9...)
      for (int i=0; i<nPho; ++i) ReweightMC_phoIdVar(i);
      //// ************************************************************* ////
    }
    
    //// ********** Apply regression energy ************* ////
    float phoStdE[500];
    for( int i=0; i<nPho; ++i)
      if( fabs(phoSCEta[i]) <= 2.5 ) {
	if( isData ){
	  float enCorrSkim = 1;//enScaleSkimEOS.energyScale( phoR9[i], phoSCEta[i], run);
	  float phoEnScale = enScale.energyScale( phoR9[i], phoSCEta[i], run)/enCorrSkim;
	  phoRegrE[i]  *= phoEnScale;
	  phoE[i]      *= phoEnScale;
	}
	phoStdE[i] = phoE[i];
	phoE[i]   = phoRegrE[i];
	
	/// transform calo position abd etaVtx, phiVtx with SC position
	for( int x = 0 ; x < 3; x++ )  phoCaloPos[i][x] = phoSCPos[i][x];
	for( int ivtx = 0 ; ivtx < nVtxBS; ivtx++ ) {
	  TVector3 xxi = getCorPhotonTVector3(i,ivtx);
	  phoEtaVtx[i][ivtx] = xxi.Eta();
	  phoPhiVtx[i][ivtx] = xxi.Phi();
	}
	
	/// additionnal smearing to go to data energy resolution
	phoRegrSmear[i] = phoE[i]*overSmearHCP.meanOverSmearing(phoSCEta[i],phoR9[i],isInGAP_EB(i),0);
	phoEt[i] = phoE[i] / cosh(phoEta[i]);  
      }    
    //// ************************************************* ////
     

    /// lepton selection
    int iElecVtx(-1), iMuonVtx(-1);
    vector<int> elecIndex = selectElectronsHCP2012( wei, iElecVtx );
    vector<int> muonIndex = selectMuonsHCP2012(     wei, iMuonVtx );

    vector<int>             event_vtx; 
    vector<int>             event_ilead ;
    vector<int>             event_itrail;
    vector<TLorentzVector>  event_plead ;
    vector<TLorentzVector>  event_ptrail;
    TLorentzVector leptag;
    
    int lepCat = -1;
    bool exitLoop = false;
    for( int ii = 0     ; ii < nPho ; ++ii ) {
      for( int jj = (ii+1); jj < nPho ; ++jj ) {
	// Preselection 2nd leg
	if (DoPreselection && !preselectPhoton(ii,phoEt[ii])) continue;
	if (DoPreselection && !preselectPhoton(jj,phoEt[jj])) continue;
	
	/// define i, j locally, so when they are inverted this does not mess up the loop
	int i = ii; 
	int j = jj;
	if(phoEt[j] > phoEt[i]){ i = jj; j = ii; }	  
	
	// Select vertex
	int selVtx  = 0;
	TLorentzVector gi,gj;
	double mij(-1);
	
	vector<int> selVtxIncl;      
	if(_config->vtxSelType()==0)
	  selVtxIncl = getSelectedVertex(i,j,true,true );
	else //use sumpt2 ranking
	  selVtxIncl = selVtxSumPt2;
	selVtx = selVtxIncl[0];
	if( selVtx < 0 ) continue;

	/// check lepton tag
	if( muonIndex.size() > 0 ) {
	  //selVtx = iMuonVtx;	  
	  leptag.SetPtEtaPhiM( muPt[muonIndex[0]], muEta[muonIndex[0]], muPhi[muonIndex[0]],0);
	  if( selectTwoPhotons(i,j,selVtx,gi,gj,vetoElec) ) {
	    lepCat = 0;
	  }
	}
	
	/// check electron tag only if muon tag failed
	if( elecIndex.size() > 0 && lepCat == -1 ) {
	  //selVtx = iElecVtx;
	  leptag.SetPtEtaPhiM( elePt[elecIndex[0]], eleEta[elecIndex[0]], elePhi[elecIndex[0]],0);
	  if( selectTwoPhotons(i,j,selVtx,gi,gj,vetoElec) ) {
	    lepCat = 1;
	    if( fabs( (leptag+gi).M() - 91.19 ) < 10 || fabs( (leptag+gj).M() - 91.19 ) < 10 ) lepCat = -1;
	    /// this is not actually the cut, but it should be but ok (dR(pho,eleTrk) > 1 no dR(pho,anyTrk) > 1 )
	    if(phoCiCdRtoTrk[i] < 1 || phoCiCdRtoTrk[j] <1 ) lepCat = -1;
	  }
	}
	

	if( lepCat >= 0 ) {
	  mij = (gi+gj).M();
          if( _config->analysisType() == "MVA" )
	        if( gi.Pt() / mij < 45./120. || gj.Pt() / mij < 30./120. ) lepCat = -1;
          if( _config->analysisType() == "baselineCiC4PF" )
	        if( gi.Pt() / mij < 45./120. || gj.Pt() < 25. ) lepCat = -1;
	  if( leptag.DeltaR(gi) < 1.0  || leptag.DeltaR(gj) < 1.0  ) lepCat = -1;
	}
	if( lepCat >= 0 ) {
	  cout << " ****** keep leptag event pts[photons] i: " << i << " j: " << j << "   -> event: " << ientry <<  endl;
	  cout << "        leptonCat: " << lepCat << endl;
	  /// if one pair passes lepton tag then no need to go further
	  /// fill in variables
	  event_vtx.resize(   1); event_vtx[0]    = selVtx;
	  event_ilead.resize( 1); event_ilead[0]  = i;
	  event_itrail.resize(1); event_itrail[0] = j;
	  event_plead.resize( 1); event_plead[0]  = gi;
	  event_ptrail.resize(1); event_ptrail[0] = gj;
	  exitLoop = true;
	  break;	
	} else {
	  /// inclusive + VBF + MetTag preselection
	  
	  /// apply kinematic cuts
	  if( !selectTwoPhotons(i,j,selVtx,gi,gj,vetoElec) ) continue;
	  /// drop photon pt cuts from inclusive cuts (add them in categorisation only)
	  mij = (gi+gj).M();	
	  if( ! _config->doSkimming() && 
	      ( gi.Pt()     < _config->pt1Cut() || gi.Pt() < _config->pt2Cut() ||
		gi.Pt()/mij < _config->loosePt1MCut() ||
		gj.Pt()/mij < _config->loosePt2MCut() ) ) continue;
	}
	
	/// here i = lead; j = trail (selectTwoPhotons does that)
	/// fill in variables
	event_vtx.push_back( selVtx );
	event_ilead.push_back(   i  );
	event_itrail.push_back(  j  );
	event_plead.push_back(  gi  );
	event_ptrail.push_back( gj  );   	  
      }
      if( exitLoop ) break;
    }
      
    if(event_ilead.size()==0 || event_itrail.size()==0)continue;
    if(event_vtx.size() == 0 ) continue;  // no pairs selected
    nEvts[icutlevel++]++;

    // Now decide which photon-photon pair in the event to select
    // for lepton tag (size of arrays is 1, so dummy selection)
    unsigned int selectedPair = 0;
    float sumEt = -1;
    for (unsigned int p=0; p < event_vtx.size(); p++) {
      float tempSumEt = event_plead[p].Pt() + event_ptrail[p].Pt();
      if( tempSumEt > sumEt) {
	sumEt = tempSumEt;
      selectedPair = p;
      }
    } 
    

    int ilead  = event_ilead[  selectedPair ];
    int itrail = event_itrail[ selectedPair ];
    int selVtx = event_vtx[    selectedPair ];
    TLorentzVector glead  = event_plead[selectedPair];
    TLorentzVector gtrail = event_ptrail[selectedPair];
    TLorentzVector hcand  = glead + gtrail;

    int CAT4 = cat4(phoR9[ilead], phoR9[itrail], phoSCEta[ilead], phoSCEta[itrail]);
    
    if( glead.Pt()  < _config->pt1Cut() ) continue;
    if( gtrail.Pt() < _config->pt2Cut() ) continue;
    if( hcand.M()   < _config->mggCut() ) continue;
    nEvts[icutlevel++]++;

    _minitree->mtree_runNum = run;
    _minitree->mtree_evtNum = event;
    _minitree->mtree_lumiSec = lumis;

    //    TLorentzVector g1,g2;
    //    g1.SetPtEtaPhiM(phoE[ilead ]/cosh(phoEta[ilead]),phoEta[ilead ], phoPhi[ilead ], 0);
    //    g2.SetPtEtaPhiM(phoE[itrail]/cosh(phoEta[ilead]),phoEta[itrail], phoPhi[itrail], 0);
    //    TLorentzVector lgg = g1 + g2;
    //_minitree->mtree_massDefVtx = lgg.M();
    _minitree->mtree_massDefVtx = hcand.M()/sqrt(phoE[ilead]*phoE[itrail])*sqrt(phoStdE[ilead]*phoStdE[itrail]);

    // calc again vertex to get correct vertex probability (can be different from last one in loop)
    vector<int> sortedVertex;
    if(_config->vtxSelType()==0)
      sortedVertex = getSelectedVertex( ilead, itrail, true, true );
    else //use sumpt2 ranking
      sortedVertex = selVtxSumPt2;

    if( sortedVertex.size() < 2 ) sortedVertex.push_back(-1);
    if( sortedVertex.size() < 3 ) sortedVertex.push_back(-1);

    if( lepCat >= 0 ) {
      /// lepton tag
      sortedVertex[0] = selVtx;  
      sortedVertex[1] = -1; 
      sortedVertex[2] = -1; 
      //      vertProb = 1;
    } 

    _minitree->mtree_rho   = rho2012;
    _minitree->mtree_rho25 = rho25;    
    _minitree->mtree_zVtx  = vtxbs[selVtx][2];
    _minitree->mtree_nVtx  = nVtxBS;
    _minitree->mtree_ivtx1 = selVtx;
    _minitree->mtree_ivtx2 = sortedVertex[1];
    _minitree->mtree_ivtx3 = sortedVertex[2];
    _minitree->mtree_vtxProb = vertProb;
    _minitree->mtree_vtxMva  = vertMVA;

    _minitree->mtree_mass  = hcand.M();
    _minitree->mtree_pt    = hcand.Pt();
    _minitree->mtree_piT   = hcand.Pt()/hcand.M();
    _minitree->mtree_y     = hcand.Rapidity();

    /// spin variables
    TLorentzVector gtmp1 = glead;  gtmp1.Boost( -hcand.BoostVector() );
    TLorentzVector gtmp2 = gtrail; gtmp2.Boost( -hcand.BoostVector() );
    _minitree->mtree_cThetaLead_heli  = cos( gtmp1.Angle(hcand.BoostVector()) );
    _minitree->mtree_cThetaTrail_heli = cos( gtmp2.Angle(hcand.BoostVector()) );
    _minitree->mtree_cThetaStar_CS    = 2*(glead.E()*gtrail.Pz() - gtrail.E()*glead.Pz())/(hcand.M()*sqrt(hcand.M2()+hcand.Pt()*hcand.Pt()));
    
    /// fill photon id variables in main tree
    _minitree->mtree_minR9      = +999;
    _minitree->mtree_minPhoIdEB = +999;
    _minitree->mtree_minPhoIdEE = +999;
    _minitree->mtree_maxSCEta   =   -1;
    _minitree->mtree_minSCEta   = +999;
    for( int i = 0 ; i < 2; i++ ) {
      int ipho = -1;
      if( i == 0 ) ipho = ilead;
      if( i == 1 ) ipho = itrail;
      fillPhotonVariablesToMiniTree( ipho, selVtx, i );      
      if( _minitree->mtree_r9[i] < _minitree->mtree_minR9 ) _minitree->mtree_minR9 = _minitree->mtree_r9[i];
      if( fabs( _minitree->mtree_sceta[i] ) <  1.5 &&  _minitree->mtree_mvaid[i] <  _minitree->mtree_minPhoIdEB ) _minitree->mtree_minPhoIdEB = _minitree->mtree_mvaid[i];
      if( fabs( _minitree->mtree_sceta[i] ) >= 1.5 &&  _minitree->mtree_mvaid[i] <  _minitree->mtree_minPhoIdEE ) _minitree->mtree_minPhoIdEE = _minitree->mtree_mvaid[i];
      if( fabs( _minitree->mtree_sceta[i] ) > _minitree->mtree_maxSCEta ) _minitree->mtree_maxSCEta =  fabs(_minitree->mtree_sceta[i]);
      if( fabs( _minitree->mtree_sceta[i] ) < _minitree->mtree_minSCEta ) _minitree->mtree_minSCEta =  fabs(_minitree->mtree_sceta[i]);
    }
    
    //------------ compute diphoton mva (add var to minitree inside function) ----------------//
    massResoCalc.setP4CalPosVtxResoSmear( glead,gtrail, 
					  TVector3(phoCaloPos[ilead ][0], phoCaloPos[ilead ][1],phoCaloPos[ilead ][2]),
					  TVector3(phoCaloPos[itrail][0], phoCaloPos[itrail][1],phoCaloPos[itrail][2]),
					  TVector3(vtxbs[selVtx][0], vtxbs[selVtx][1], vtxbs[selVtx][2]),
					  _minitree->mtree_relResOverE, _minitree->mtree_relSmearing );

    
    _minitree->mtree_massResoTot = massResoCalc.relativeMassResolutionFab_total( vertProb );    
    _minitree->mtree_massResoEng = massResoCalc.relativeMassResolutionFab_energy( );    
    _minitree->mtree_massResoAng = massResoCalc.relativeMassResolutionFab_angular();    
   
    float diphotonmva = DiPhoID_MVA( glead, gtrail, hcand, massResoCalc, vertProb, 
				     _minitree->mtree_mvaid[0],_minitree->mtree_mvaid[1] );

    
    // ---- Start categorisation ---- //
    _minitree->mtree_lepTag  = 0;
    _minitree->mtree_metTag  = 0;
    _minitree->mtree_vbfTag  = 0;
    _minitree->mtree_hvjjTag = 0;

    // 1. lepton tag
    if( lepCat >= 0 ) {
      _minitree->mtree_lepTag = 1;
      _minitree->mtree_lepCat = lepCat;
      _minitree->mtree_fillLepTree  = true;
      // if( lepCat == 0 ) fillMuonTagVariables(lepTag,glead,gtrail,elecIndex[0],selVtx);
      // if( lepCat == 1 ) fillElecTagVariables(lepTag,glead,gtrail,muonIndex[0],selVtx);
    }

    // 3. met tag (For the jet energy regression, MET needs to be corrected first.)
    _minitree->mtree_rawMet    = recoPfMET;
    _minitree->mtree_rawMetPhi = recoPfMETPhi;
    //    if( !isData ) {
      /// bug in data skim, met correction already applied
      //3.1 Soft Jet correction (FC?)    
      applyJEC4SoftJets();
      //3.2 smearing
      if( !isData ) METSmearCorrection(ilead, itrail);
      //3.3 shifting (even in data? but different in data and MC)
      METPhiShiftCorrection();
      //3.4 scaling
      if( isData) METScaleCorrection(ilead, itrail);
      //    }
    _minitree->mtree_corMet    = recoPfMET;
    _minitree->mtree_corMetPhi = recoPfMETPhi;
    
    // 2. dijet tag
    Int_t nVtxJetID = -1;
    if( _config->doPUJetID() ) nVtxJetID = nVtxBS;
    //vector<int> goodJetsIndex = selectJets( ilead, itrail, nVtxJetID, wei, selVtx );
    vector<int> goodJetsIndex = selectJetsJEC(  ilead, itrail, nVtxJetID, wei, selVtx );
    int vbftag(-1),hstratag(-1),catjet(-1);
    dijetSelection( glead, gtrail, goodJetsIndex, wei, selVtx, vbftag, hstratag, catjet);
    _minitree->mtree_vbfTag  = vbftag;
    _minitree->mtree_hvjjTag = hstratag;
    _minitree->mtree_vbfCat  = catjet;      

    // 2x. radion analysis

    // take the very same photon candidates as in the H->GG analysis above
    _minitree->radion_evtNum = event;
    *(_minitree->radion_gamma1) = glead;
    *(_minitree->radion_gamma2) = gtrail;

    vector<int> goodJetsIndexRadion = selectJetsRadion(nVtxJetID, selVtx);
    _minitree->radion_bJetTags->Set(goodJetsIndexRadion.size());
    _minitree->radion_jet_genJetPt        ->Set(goodJetsIndexRadion.size());
    _minitree->radion_jet_eta             ->Set(goodJetsIndexRadion.size());
    _minitree->radion_jet_cef		  ->Set(goodJetsIndexRadion.size());
    _minitree->radion_jet_nef		  ->Set(goodJetsIndexRadion.size());
    _minitree->radion_jet_mef		  ->Set(goodJetsIndexRadion.size());
    _minitree->radion_jet_nconstituents	  ->Set(goodJetsIndexRadion.size());
    _minitree->radion_jet_chf		  ->Set(goodJetsIndexRadion.size());
    _minitree->radion_jet_JECUnc	  ->Set(goodJetsIndexRadion.size());
    _minitree->radion_jet_ptLeadTrack	  ->Set(goodJetsIndexRadion.size());
    _minitree->radion_jet_vtxPt		  ->Set(goodJetsIndexRadion.size());
    _minitree->radion_jet_vtx3dL	  ->Set(goodJetsIndexRadion.size());
    _minitree->radion_jet_SoftLeptPtCut	  ->Set(goodJetsIndexRadion.size());
    _minitree->radion_jet_dPhiMETJet	  ->Set(goodJetsIndexRadion.size());
    _minitree->radion_jet_nch		  ->Set(goodJetsIndexRadion.size());
    _minitree->radion_jet_vtx3deL	  ->Set(goodJetsIndexRadion.size());
    _minitree->radion_jet_vtxMass	  ->Set(goodJetsIndexRadion.size());
    _minitree->radion_jet_ptRaw		  ->Set(goodJetsIndexRadion.size());
    _minitree->radion_jet_EnRaw		  ->Set(goodJetsIndexRadion.size());
    _minitree->radion_jet_SoftLeptptRelCut->Set(goodJetsIndexRadion.size());
    _minitree->radion_jet_SoftLeptdRCut	  ->Set(goodJetsIndexRadion.size());
    _minitree->radion_jet_partonID	  ->Set(goodJetsIndexRadion.size());
    _minitree->radion_jet_dRJetGenJet         ->Set(goodJetsIndexRadion.size());
    _minitree->radion_MET = recoPfMET;
    _minitree->radion_rho25 = rho25;

    for (unsigned i = 0; i < goodJetsIndexRadion.size(); i++) {
      int iJet = goodJetsIndexRadion[i];

      //_minitree->radion_bJetTags->AddAt(jetCombinedSecondaryVtxMVABJetTags[iJet], i);
      _minitree->radion_bJetTags->AddAt(jetCombinedSecondaryVtxBJetTags[iJet], i);
      _minitree->radion_jet_genJetPt         ->AddAt(jetGenJetPt[iJet], i);
      _minitree->radion_jet_eta              ->AddAt(jetEta[iJet], i);
      _minitree->radion_jet_cef		     ->AddAt(jetCEF[iJet], i);
      _minitree->radion_jet_nef		     ->AddAt(jetNEF[iJet], i);
      _minitree->radion_jet_mef		     ->AddAt(jetMEF[iJet], i);
      _minitree->radion_jet_nconstituents    ->AddAt(jetNConstituents[iJet], i);
      _minitree->radion_jet_chf		     ->AddAt(jetCHF[iJet], i);
      _minitree->radion_jet_JECUnc	     ->AddAt(jetJECUnc[iJet], i);
      _minitree->radion_jet_ptLeadTrack	     ->AddAt(jetLeadTrackPt[iJet], i);
      _minitree->radion_jet_vtxPt	     ->AddAt(jetVtxPt[iJet], i);
      _minitree->radion_jet_vtx3dL	     ->AddAt(jetVtx3dL[iJet], i);
      _minitree->radion_jet_SoftLeptPtCut    ->AddAt(jetSoftLeptPt[iJet], i);
      _minitree->radion_jet_nch		     ->AddAt(jetNCH[iJet], i);
      _minitree->radion_jet_vtx3deL	     ->AddAt(jetVtx3deL[iJet], i);
      _minitree->radion_jet_vtxMass	     ->AddAt(jetVtxMass[iJet], i);
      _minitree->radion_jet_ptRaw	     ->AddAt(jetRawPt[iJet], i);
      _minitree->radion_jet_EnRaw	     ->AddAt(jetRawEn[iJet], i);
      _minitree->radion_jet_SoftLeptptRelCut ->AddAt(jetSoftLeptPtRel[iJet], i);
      _minitree->radion_jet_SoftLeptdRCut    ->AddAt(jetSoftLeptdR[iJet], i);
      _minitree->radion_jet_partonID	     ->AddAt(jetPartonID[iJet], i);
      _minitree->radion_jet_dRJetGenJet      ->AddAt(sqrt(pow(jetEta[iJet]-jetGenEta[iJet],2)+pow(jetPhi[iJet]-jetGenPhi[iJet],2)), i);
      float tmpPi = 3.1415927, tmpDPhi=fabs(jetPhi[iJet]-recoPfMETPhi);
      if(tmpDPhi>tmpPi) tmpDPhi=2*tmpPi-tmpDPhi;
      _minitree->radion_jet_dPhiMETJet	     ->AddAt(tmpDPhi, i);

      TLorentzVector* jet = new((*(_minitree->radion_jets))[_minitree->radion_jets->GetEntriesFast()]) TLorentzVector();
      jet->SetPtEtaPhiE(jetPt[iJet], jetEta[iJet], jetPhi[iJet], jetEn[iJet]);
    }

    // Continue step 3.
    if (  MetTagSelection(glead,gtrail,goodJetsIndex) && _minitree->mtree_vbfTag == 0 && _minitree->mtree_lepTag == 0   && 
	 _minitree->mtree_corMet > 70.  &&	 
	 fabs( phoSCEta[ilead] ) < 1.45 && fabs( phoSCEta[itrail]) < 1.45 ) _minitree->mtree_metTag = 1;

    //----------- categorisation (for now incl + vbf + lep + met) -----------//
    _minitree->mtree_catBase = CAT4;
    _minitree->mtree_catMva  = -1;
    for( int icat_mva = 0 ; icat_mva < 4; icat_mva++ )
      if( diphotonmva >= Ddipho_cat[icat_mva] ) { _minitree->mtree_catMva = icat_mva; break; }
    if       ( _minitree->mtree_lepTag == 1 ) {
      _minitree->mtree_catBase = _minitree->mtree_lepCat + 6;
      _minitree->mtree_catMva  = _minitree->mtree_lepCat + 6;
    } else if( _minitree->mtree_vbfTag == 1 ) {
      _minitree->mtree_catBase = _minitree->mtree_vbfCat + 4;
      _minitree->mtree_catMva  = _minitree->mtree_vbfCat + 4;
    } else if( _minitree->mtree_metTag == 1 ) {
      _minitree->mtree_catBase = 8;
      _minitree->mtree_catMva  = 8;
    }
    if( diphotonmva < Ddipho_cat[3] )  _minitree->mtree_catMva  = -1;
    
    /// photon pt cut was dropped from the inclusive cuts
    if(  _minitree->mtree_catMva  < 4 && (glead.Pt()/hcand.M() < 1./3. || gtrail.Pt()/hcand.M() < 1./4.) ) 
       _minitree->mtree_catMva  = -1;

    if(  _minitree->mtree_catBase < 4 && (glead.Pt()/hcand.M() < 1./3. || gtrail.Pt()/hcand.M() < 1./4.) ) 
       _minitree->mtree_catBase  = -1;
    
    //------------ MC weighting factors and corrections    
    if( !isData ) {
      /// needs to be recomputed for each event (because reinit var for each event)
      _minitree->mc_wNgen = 100000./_weight_manager->getNevts();
      _minitree->mc_wXsec  = _weight_manager->xSecW(mc_whzh_type);      
      if( ( mode_ == 3 ||  mode_ == 19 ) && isprompt1 == 1 ) _minitree->mc_wXsec  *= 1.3;
      _minitree->mc_wBSz   = _weight_manager->bszW(vtxbs[selVtx][2]-mcVtx[0][2]);
      _minitree->mc_wVtxId = _weight_manager->vtxPtCorrW( hcand.Pt() );
      
      /// photon identification
      float wPhoId[] = { 1., 1.};
      for( int i = 0 ; i < 2; i++ ) {
	wPhoId[i] = 1;
	int index = -1;
	if( i == 0 ) index = ilead;
	if( i == 1 ) index = itrail;
	wPhoId[i] *= _weight_manager->phoIdPresel(phoR9[index],phoSCEta[index]);
	if( _config->analysisType() == "baselineCiC4PF" ) wPhoId[i] *= _weight_manager->phoIdCiC(phoR9[index],phoSCEta[index]);
	if( _config->analysisType() == "MVA"            ) wPhoId[i] *= _weight_manager->phoIdMVA(phoR9[index],phoSCEta[index]);
	if( vetoElec[i] ) wPhoId[i] *= _weight_manager->phoIdEleVeto(phoR9[index],phoSCEta[index]);	      
      }
      _minitree->mc_wPhoEffi   = wPhoId[0]*wPhoId[1];
      
      /// trigger efficiency
      _minitree->mc_wTrigEffi = 0.9968; /// FIX ME

      /// cross section volontary not included in total weight
      _minitree->mc_wei = 
	_minitree->mc_wPU       *
	_minitree->mc_wBSz      *
	_minitree->mc_wHQT      *  /// = 1 but in 2011
	_minitree->mc_wVtxId    *
	_minitree->mc_wPhoEffi  *
	_minitree->mc_wTrigEffi *
	_minitree->mc_wNgen;

      wei =  _minitree->mc_wei;
    }
    nEvts[icutlevel++]++;
    if( _minitree->mtree_lepTag ) nEvts[icutlevel+0]++;
    if( _minitree->mtree_vbfTag ) nEvts[icutlevel+1]++;
    
    //// following crap can be removed when the synchornization will be successfull. 
    if( DoDebugEvent ) {
      _minitree->setSynchVariables();
      _xcheckTextFile << " pho1 pos: " << phoPos[ilead]  << endl;
      _xcheckTextFile << " ieta1 : " << phoSeedDetId1[ilead] << " iphi1: " << phoSeedDetId2[ilead] << endl;
      _xcheckTextFile << " pho2 pos: " << phoPos[itrail] << endl;
      _xcheckTextFile << " ieta1 : " << phoSeedDetId1[itrail] << " iphi1: " << phoSeedDetId2[itrail] << endl;

      _xcheckTextFile << " oversmear 1: " << overSmear.meanOverSmearing(phoSCEta[ilead],phoR9[ilead]  ,isInGAP_EB(ilead),0) << endl;
      _xcheckTextFile << " oversmear 2: " << overSmear.meanOverSmearing(phoSCEta[itrail],phoR9[itrail],isInGAP_EB(itrail),0) << endl;
      _xcheckTextFile << " mass reso (eng only): " << _minitree->mtree_massResoEng << endl;
      _xcheckTextFile << " mass reso (ang only): " << _minitree->mtree_massResoAng << endl;

      for( unsigned i = 0 ; i < _minitree->sync_iName.size(); i++ )
	cout  << _minitree->sync_iName[i] << ":" << *_minitree->sync_iVal[i]  << "  ";
      for( unsigned i = 0 ; i < _minitree->sync_lName.size(); i++ )
	cout << _minitree->sync_lName[i] << ":" << *_minitree->sync_lVal[i]  << "  ";
      for( unsigned i = 0 ; i < _minitree->sync_fName.size(); i++ )
	cout << _minitree->sync_fName[i] << ":" << *_minitree->sync_fVal[i]  << "  ";
      cout << endl;	
      

      cout << "  myVtx = " << selVtx << "; 1=" << sortedVertex[1] << " 2= " << sortedVertex[2] << endl;
      for( int ivtx = 0; ivtx < nVtxBS; ivtx++ ) {
	cout << " etas[ ivtx = " << ivtx << "] = " << phoEtaVtx[ilead][ivtx] << " - " << phoEtaVtx[itrail][ivtx] << "  - zVtx = " << vtxbs[ivtx][2] << endl;

      }
    }

    _minitree->fill();    
    if( _config->doSkimming() && tSkim ) {
      /// undo all modifs before filling the skim
      fChain->GetEntry(jentry);
      tSkim->Fill();
    }
    //---------------      
    
  //   }    
  }// end for entry
  if( _config->doSkimming() ) {
    _minitree->mtree_file->cd();
    TH1F *hEvents = new TH1F("hEvents","hEvents",2,0,2);
    hEvents->SetBinContent(1,_weight_manager->getNevts());
    hEvents->SetBinContent(2,nEvts[nEvts.size()-1]);
    hEvents->Write();
    tSkim->Write();
    _minitree->mtree_file->Close();
  } else  _minitree->end();

  for( unsigned icut = 0 ; icut < nEvts.size(); icut++ )
    cout << nCutName[icut] << nEvts[icut] << endl;
  
  delete rnd;  

  return nEvts[nEvts.size()-1];
}
Exemple #25
0
void test_allEvt::ComputeAllVarPietro(TLorentzVector lepP,TLorentzVector lepN){
  // Preliminary definitions:

  const double pbeam = 7000.; // exact number irrelevant as long as pbeam >> Mprot
  const double Mprot = 0.9382720;
  const double Mlepton = 0.10566;  // (muon)
  const double gPI = TMath::Pi();
  const double Ebeam = sqrt( pbeam*pbeam + Mprot*Mprot );
  TLorentzVector beam1_LAB( 0., 0., pbeam, Ebeam );
  TLorentzVector beam2_LAB( 0., 0., -pbeam, Ebeam );


  // assuming that we have a TTree "data" (data ntuple) containing the 4-vectors lepP and lepN of lepton and antilepton

  // event by event (in some loop over dilepton events in the data ntuple):


  // data->GetEvent( i_event );

  // double lepP_pT  = lepP->Pt();
  // double lepN_pT  = lepN->Pt();

  // double lepP_eta = lepP->PseudoRapidity();
  // double lepN_eta = lepN->PseudoRapidity();

  // dilepton 4-vector:

  TLorentzVector dilepton = lepP + lepN;
  double pT   = dilepton.Pt();
  double rap  = dilepton.Rapidity();
  double mass = dilepton.M();

  // calculation of decay angles in three polarization frames

  // reference directions to calculate angles:

  TVector3 lab_to_dilep = -dilepton.BoostVector();

  TLorentzVector beam1_DILEP = beam1_LAB;
  beam1_DILEP.Boost(lab_to_dilep);         // beam1 in the dilepton rest frame
  TLorentzVector beam2_DILEP = beam2_LAB;
  beam2_DILEP.Boost(lab_to_dilep);         // beam2 in the dilepton rest frame

  TVector3 beam1_direction     = beam1_DILEP.Vect().Unit();
  TVector3 beam2_direction     = beam2_DILEP.Vect().Unit();
  TVector3 dilep_direction     = dilepton.Vect().Unit();
  TVector3 beam1_beam2_bisect  = ( beam1_direction - beam2_direction ).Unit();


  // all polarization frames have the same Y axis = the normal to the plane formed by
  // the directions of the colliding hadrons:

  TVector3 Yaxis = ( beam1_direction.Cross( beam2_direction ) ).Unit();

  // flip of y axis with rapidity:

  if ( rap < 0. ) Yaxis = - Yaxis;

  TVector3 perpendicular_to_beam = ( beam1_beam2_bisect.Cross( Yaxis ) ).Unit();


  // positive lepton in the dilepton rest frame:

  TLorentzVector lepton_DILEP = lepP;
  lepton_DILEP.Boost(lab_to_dilep);

  // CS frame angles:

  TVector3 newZaxis = beam1_beam2_bisect;
  TVector3 newYaxis = Yaxis;
  TVector3 newXaxis = newYaxis.Cross( newZaxis );

  TRotation rotation;
  rotation.SetToIdentity();
  rotation.RotateAxes( newXaxis, newYaxis, newZaxis );
  rotation.Invert();  // transforms coordinates from the "xyz" frame to the new frame
  TVector3 lepton_DILEP_rotated = lepton_DILEP.Vect();
  lepton_DILEP_rotated.Transform(rotation);

  /* double */ costh_CS = lepton_DILEP_rotated.CosTheta();
  /* double */ phi_CS   = lepton_DILEP_rotated.Phi() * 180. / gPI;
  double phith_CS;
  if ( costh_CS < 0. ) phith_CS = phi_CS - 135.;
  if ( costh_CS > 0. ) phith_CS = phi_CS - 45.;
  if ( phith_CS < -180. ) phith_CS = 360. + phith_CS;
  phi_CS   = phi_CS / 180. * gPI;


  // HELICITY frame angles:

  newZaxis = dilep_direction;
  newYaxis = Yaxis;
  newXaxis = newYaxis.Cross( newZaxis );

  rotation.SetToIdentity();
  rotation.RotateAxes( newXaxis, newYaxis, newZaxis );
  rotation.Invert();
  lepton_DILEP_rotated = lepton_DILEP.Vect();
  lepton_DILEP_rotated.Transform(rotation);

  /* double */ costh_HX = lepton_DILEP_rotated.CosTheta();
  /* double */ phi_HX   = lepton_DILEP_rotated.Phi() * 180. / gPI;
  double phith_HX;
  if ( costh_HX < 0. ) phith_HX = phi_HX - 135.;
  if ( costh_HX > 0. ) phith_HX = phi_HX - 45.;
  if ( phith_HX < -180. ) phith_HX = 360. + phith_HX;
  phi_HX   = phi_HX / 180. * gPI;


  // // PERPENDICULAR HELICITY frame angles:

  // newZaxis = perpendicular_to_beam;
  // newYaxis = Yaxis;
  // newXaxis = newYaxis.Cross( newZaxis );

  // rotation.SetToIdentity();
  // rotation.RotateAxes( newXaxis, newYaxis, newZaxis );
  // rotation.Invert();
  // lepton_DILEP_rotated = lepton_DILEP.Vect();
  // lepton_DILEP_rotated.Transform(rotation);

  // double costh_PX = lepton_DILEP_rotated.CosTheta();
  // double phi_PX   = lepton_DILEP_rotated.Phi() * 180. / gPI;
  // double phith_PX;
  // if ( costh_PX < 0. ) phith_PX = phi_PX - 135.;
  // if ( costh_PX > 0. ) phith_PX = phi_PX - 45.;
  // if ( phith_PX < -180. ) phith_PX = 360. + phith_PX;
  // phi_PX   = phi_PX / 180. * gPI;



}