-
Notifications
You must be signed in to change notification settings - Fork 1
/
runXSecLooper.cpp
125 lines (110 loc) · 4.81 KB
/
runXSecLooper.cpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
#include "GENIEXSecExtract/XSecLooper.h"
#include "TFile.h"
#include "TH1.h"
#include "TH2.h"
#include <PlotUtils/MnvH1D.h>
#include <PlotUtils/MnvH2D.h>
#include <cstdlib>
typedef unsigned int uint;
class MinModDepCCQEXSec : public XSec
{
public:
MinModDepCCQEXSec(const char* name)
:XSec(name)
{
};
bool isCCInclusiveSignal( ChainWrapper& chw, int entry )
{
double theta = 0.;
double true_muon_px = (double)chw.GetValue("mc_primFSLepton",entry,0)/1000;
double true_muon_py = (double)chw.GetValue("mc_primFSLepton",entry,1)/1000;
double true_muon_pz = (double)chw.GetValue("mc_primFSLepton",entry,2)/1000;
double numi_beam_angle_rad = -0.05887;
double pyprime = -1.0*sin(numi_beam_angle_rad)*true_muon_pz + cos(numi_beam_angle_rad)*true_muon_py;
double pzprime = 1.0*cos(numi_beam_angle_rad)*true_muon_pz + sin(numi_beam_angle_rad)*true_muon_py;
double pSquare = pow(true_muon_px,2) + pow(pyprime,2) + pow(pzprime,2);
theta = acos( pzprime / sqrt(pSquare) );
theta *= 180./3.14159;
double pT = sqrt(pSquare) * sin(theta);
int npdg = chw.GetValue("mc_nFSPart", entry);
int npions = 0;
for (int i = 0; i < npdg; i++)
{
int pdg = chw.GetValue("mc_FSPartPDG", entry, i);
if (pdg == 211) npions++;
}
//if(!chw.GetValue("truth_is_fiducial",entry)) return false; //Doesn't work for MasterAnaDev tuples. What does this even mean in the targets anyway? :(
if( pzprime >= 1.5 && theta <= 20.0 && npions >= 1 && pT < 1.0) return true;
if(npions >=0) return true;
return false;
}
// Override this method from the base class to decide what events to
// include in this selection
virtual bool passesCuts(ChainWrapper& chw, int entry)
{
if((int)chw.GetValue("mc_incoming", entry)!=14) return false;
if((int)chw.GetValue("mc_current", entry)!=1) return false;
int npdg = chw.GetValue("mc_nFSPart", entry);
int npions = 0;
for (int i = 0; i < npdg; i++)
{
int pdg = chw.GetValue("mc_FSPartPDG", entry, i);
if (pdg == 211) npions++;
}
if(npions == 0) return false;
if(!isCCInclusiveSignal ( chw, entry ) ) return false;
return true;
}
};
int main(const int argc, const char** argv)
{
//Read a playlist file from the command line
if(argc != 2)
{
std::cerr << "Expected exactly 1 command line argument, but got " << argc - 1 << ".\n\n"
<< "USAGE: runXSecLooper <MCPlaylist.txt>\n\n"
<< "MCPlaylist.txt shall contain one .root file per line that has a Truth tree in it.\n"
<< "This program returns 0 when it suceeds. It produces a .root file with GENIEXSECEXTRACT in its name.\n";
return 1;
}
const std::string playlistFile = argv[1]; //argv[0] is the name of the executable
// Create the XSecLooper and tell it the input files
// Inputs should be the merged ntuples:
XSecLooper loop(playlistFile.c_str());
// Tell the XSecLooper which neutrino type we're considering (mandatory)
loop.setNuPDG(14);
// Setting the number of Universes in the GENIE error band (default 100, put 0 if you do not want to include the universes)
loop.setNumUniv(0);
loop.setFiducial(5980, 8422);
loop.setPlaylist(PlotUtils::FluxReweighter::minervame1A);
// Add the differential cross section dsigma/ds_dpT
double pt_edges[] = { 0.0, 0.075, 0.15, 0.25, 0.325, 0.4, 0.475, 0.55, 0.7, 0.85, 1.0, 1.25, 1.5, 2.5, 4.5 };
int pt_nbins = 14;
double q2_edges[] = {0.01, 0.015, 0.020, 0.025, 0.030, 0.035, 0.040, 0.045, 0.05, 0.075, 0.10, 0.125, 0.15, 0.175,0.20, 0.25,0.30,0.35, 0.4, 0.45, 0.50, 0.55, 0.60 , 0.7, 0.80,0.9, 1.,1.1, 1.2};
int q2_nbins = (sizeof(q2_edges) / sizeof(*q2_edges)) - 1;
//int q2_nbins = 28;
std::cout << "Before MinModDepCCQEXSec*" << std::endl;
// Flux-integrated over the range 0.0 to 100.0 GeV
MinModDepCCQEXSec* ds_dpT = new MinModDepCCQEXSec("q2");
ds_dpT->setBinEdges(q2_nbins, q2_edges);
ds_dpT->setVariable(XSec::kQ2);
ds_dpT->setIsFluxIntegrated(true);
ds_dpT->setDimension(1);
ds_dpT->setFluxIntLimits(0.0, 100.0);
ds_dpT->setNormalizationType(XSec::kPerNucleon);
ds_dpT->setUniverses(0); //default value, put 0 if you do not want universes to be included.
loop.addXSec(ds_dpT);
std::cout << "AFTER MinModDepCCQEXSec*" << std::endl;
loop.runLoop();
std::cout << "AFTER MinModDepCCQEXSec* rrunLOOP" << std::endl;
// Get the output histograms and save them to file
string geniefilename = "GENIEXSECEXTRACT_" + playlistFile.substr(playlistFile.rfind("/")+1, playlistFile.find(".")) + ".root";
TFile fout(geniefilename.c_str(), "RECREATE");
for(uint i=0; i<loop.getXSecs().size(); ++i)
{
if(i%1000==0) std::cout << i << " / " << loop.getXSecs().size() << "\r" << std::flush;
loop.getXSecs()[i]->getXSecHist()->Write();
loop.getXSecs()[i]->getEvRateHist()->Write();
}
return 0;
}