00001 #include <cassert>
00002 #include <iomanip>
00003
00004 #include "MessageService/MsgService.h"
00005 #include "Conventions/SimFlag.h"
00006 #include "Conventions/Detector.h"
00007 #include "Conventions/Munits.h"
00008 #include "DataUtil/infid.h"
00009
00010 #include "NtupleUtils/NuEvent.h"
00011 #include "NtupleUtils/NuMCEvent.h"
00012 #include "NtupleUtils/NuCut.h"
00013
00014 #include "TString.h"
00015
00016 CVSID("$Id: NuCut.cxx,v 1.14 2010/02/01 14:26:46 bckhouse Exp $");
00017
00019
00020 NuCut::NuCut(TString name, const NuPlots *plots) :
00021 fFidVol(),
00022 fSelName(name),
00023 fPlots(plots),
00024 fPassCuts(true)
00025 {
00026 fEventCount = 0;
00027 fAnaVersion = AnaVersionHash(name);
00028 }
00030
00031 NuCut::~NuCut()
00032 {
00033
00034 }
00035
00037
00038
00039 Bool_t NuCut::MakeCuts(const NuEvent &nu)
00040 {
00041
00042 ResetStatus();
00043
00044 MakePreselectionCuts(nu);
00045 MakeSelectionCuts(nu);
00046
00047 return fPassCuts;
00048 }
00049
00051
00052
00053 Bool_t NuCut::MakePreselectionCuts(const NuEvent &nu)
00054 {
00055 Preselection(nu);
00056 MAXMSG("NuCut",Msg::kDebug,50) << "Passed " << GetName() << " Preselection = " << (fPassCuts ? "Yes" : "No") << endl;
00057 return fPassCuts;
00058 }
00059
00061
00062
00063 Bool_t NuCut::MakeSelectionCuts(const NuEvent &nu)
00064 {
00065 Selection(nu);
00066 return fPassCuts;
00067 }
00068
00070
00071
00072 void NuCut::ResetStatus(void)
00073 {
00074 fPassCuts = true;
00075
00076
00077
00078 Bool_t passed = true;
00079 for (UInt_t i = 0; i < fCutList.size(); ++i) {
00080
00081 TString &cutname = fCutList[i].first;
00082 Bool_t passcut = fCutList[i].second;
00083
00084
00085 UInt_t sumindex;
00086 for (sumindex = 0; sumindex < fCutTotals.size(); ++sumindex)
00087 {
00088 if (fCutTotals[sumindex].first == cutname) break;
00089 }
00090
00091
00092 if (sumindex == fCutTotals.size())
00093 {
00094
00095 fCutTotals.push_back(pair<TString,Int_t>(cutname, 0));
00096 }
00097
00098
00099
00100 passed = passed && passcut;
00101 if (passed)
00102 {
00103 fCutTotals[sumindex].second++;
00104 }
00105
00106
00107
00108 }
00109
00110
00111 if (!fCutList.empty()) fEventCount++;
00112
00113
00114 fCutList.clear();
00115 }
00116
00118
00119 Bool_t NuCut::Cut_If(Bool_t condition, const TString &s)
00120 {
00121 fPassCuts = fPassCuts && (!condition);
00122
00123
00124 fCutList.push_back(pair<TString,Int_t>(s,!condition));
00125
00126 return fPassCuts;
00127 }
00128
00130
00131 Bool_t NuCut::Keep_If(Bool_t condition, const TString &s)
00132 {
00133 fPassCuts = fPassCuts && condition;
00134
00135
00136 fCutList.push_back(pair<TString,Int_t>(s,condition));
00137
00138 return fPassCuts;
00139 }
00140
00142
00143
00144 Bool_t NuCut::Keep_Data_If(Bool_t condition, const NuEvent &nu, const TString &name)
00145 {
00146
00147 if (nu.simFlag == SimFlag::kData)
00148 {
00149 return Keep_If(condition, name);
00150 }
00151
00152 return fPassCuts;
00153 }
00154
00156
00157
00158 Bool_t NuCut::Cut_Data_If(Bool_t condition, const NuEvent &nu, const TString &name)
00159 {
00160
00161 if (nu.simFlag == SimFlag::kData)
00162 {
00163 return Cut_If(condition, name);
00164 }
00165
00166 return fPassCuts;
00167 }
00168
00170
00171
00172 void NuCut::SetFidVol(const TString &fidvol)
00173 {
00174 if (fFidVol != "" && fidvol == "") {
00175 MSG("NuCut", Msg::kWarning) << "Setting blank fiducial volume in " << GetName() << ", but one has already been set."
00176 << "Cannot reset - will continue using whatever is set (but not forcing it)" << endl;
00177 }
00178 fFidVol = fidvol;
00179
00180 if (FidVol::getName() != fidvol) {
00181 choose_infid_set(fidvol.Data());
00182 }
00183 }
00184
00186
00187 Bool_t NuCut::InFidVol(const NuEvent &nu) const
00188 {
00189
00190 if (FidVol::getName() != fFidVol) {
00191 MSG("NuCut",Msg::kInfo) << "Fiducial volume has changed in " << GetName() << ", resetting to \"" << fFidVol << "\"" << endl;
00192
00193 if (FidVol::getName() != fFidVol) {
00194 choose_infid_set(fFidVol.Data());
00195 }
00196 }
00197
00198
00199 if (nu.ntrk == 0) {
00200 MAXMSG("NuCut",Msg::kWarning,3) << "Testing vertex against Fiducial volume, but no tracks!" << endl;
00201 }
00202
00203 return infid(static_cast<Detector::Detector_t>(nu.detector),
00204 static_cast<SimFlag::SimFlag_t>(nu.simFlag),
00205 nu.xTrkVtx,nu.yTrkVtx,nu.zTrkVtx);
00206 }
00207
00209
00210 Bool_t NuCut::InFidVolEvt(const NuEvent &nu) const
00211 {
00212
00213 if (FidVol::getName() != fFidVol) {
00214 MSG("NuCut",Msg::kInfo) << "Fiducial volume has changed in " << GetName() << ", resetting to \"" << fFidVol << "\"" << endl;
00215
00216 if (FidVol::getName() != fFidVol) {
00217 choose_infid_set(fFidVol.Data());
00218 }
00219 }
00220
00221 return infid(Detector::Detector_t(nu.detector),
00222 SimFlag::SimFlag_t(nu.simFlag),
00223 nu.xEvtVtx, nu.yEvtVtx, nu.zEvtVtx);
00224 }
00225
00227
00228 Bool_t NuCut::InFidVolTrueEvt(const NuMCEvent& mc) const
00229 {
00230
00231 if (FidVol::getName() != fFidVol) {
00232 MSG("NuCut",Msg::kInfo) << "Fiducial volume has changed in " << GetName() << ", resetting to \"" << fFidVol << "\"" << endl;
00233
00234 if (FidVol::getName() != fFidVol) {
00235 choose_infid_set(fFidVol.Data());
00236 }
00237 }
00238
00239 return infid(Detector::Detector_t(mc.detector),
00240 SimFlag::SimFlag_t(mc.simFlag),
00241 mc.vtxxMC,mc.vtxyMC,mc.vtxzMC);
00242 }
00243
00245
00246 void NuCut::Defer_Preselection(NuCut &cut, const NuEvent & nu)
00247 {
00248
00249 cut.ResetStatus();
00250
00251
00252 cut.MakePreselectionCuts(nu);
00253
00254
00255
00256
00257
00258
00259
00260
00261
00262
00263
00264
00265 for (UInt_t i = 0; i < cut.fCutList.size(); ++i) {
00266 Keep_If(cut.fCutList[i].second, cut.fCutList[i].first);
00267 }
00268 }
00269
00271
00272 void NuCut::Defer_Selection(NuCut &cut, const NuEvent & nu)
00273 {
00274
00275 cut.ResetStatus();
00276
00277
00278 cut.MakeSelectionCuts(nu);
00279
00280
00281 for (UInt_t i = 0; i < cut.fCutList.size(); ++i) {
00282 Keep_If(cut.fCutList[i].second, cut.fCutList[i].first);
00283 }
00284
00285
00286
00287
00288
00289 }
00290
00292
00293 Bool_t NuCut::Passed(TString cutname) const
00294 {
00295 for (UInt_t i = 0; i < i < fCutList.size(); ++i) {
00296 if (fCutList[i].first == cutname) {
00297 return fCutList[i].second;
00298 }
00299 }
00300 MSG("NuCut",Msg::kWarning) << "Cut " << cutname << " not found in selection " << GetName() << ". Assuming failed." << endl;
00301 PrintCurrent();
00302 return false;
00303 }
00304
00306
00307 Bool_t NuCut::PassedExcept(TString cutname) const
00308 {
00309 Bool_t found = false;
00310 Bool_t pass = true;
00311 for (UInt_t i = 0; i < fCutList.size(); ++i) {
00312 if (fCutList[i].first != cutname) {
00313 pass = pass && fCutList[i].second;
00314 } else {
00315 found = true;
00316 }
00317 }
00318 if (!found) {
00319 MSG("NuCut",Msg::kWarning) << "Cut " << cutname << " not found in selection " << GetName() << ". Just returning selection, not N-1." << endl;
00320 PrintCurrent();
00321 }
00322
00323 return pass;
00324 }
00325
00327
00328 void NuCut::PrintCurrent(void) const
00329 {
00330 MSG("NuCut",Msg::kInfo) << "Selection " << GetName() << " has " << fCutList.size() << " cuts:" << endl;
00331 for (UInt_t i = 0; i < fCutList.size(); ++i) {
00332 MSG("NuCut",Msg::kInfo) << " " << fCutList[i].first << " " << (fCutList[i].second?"Passed":"Failed") << endl;
00333 }
00334 if (Passed()) MSG("NuCut",Msg::kInfo) << " -- Event Passed" << endl;
00335 else MSG("NuCut",Msg::kInfo) << " ** Event Failed" << endl;
00336
00337 }
00338
00339
00341
00342 void NuCut::PrintSummary(void)
00343 {
00344
00345 ResetStatus();
00346
00347
00348 Int_t lsize = 12;
00349 for (UInt_t i = 0; i < fCutTotals.size(); ++i)
00350 {
00351 Int_t len = fCutTotals[i].first.Length();
00352 if (len > lsize) lsize = len;
00353 }
00354
00355 Int_t width = lsize + 20;
00356
00357 MSG("NuCut",Msg::kInfo) << setw(width/2) << right << setfill('=') << (" "+GetName()) << setw(width/2+width%2) << left << " Summary " << '\n';
00358 MSG("NuCut",Msg::kInfo) << setw(lsize) << left << setfill(' ') << "Cut" << " # Passed % Passed\n";
00359
00360 MSG("NuCut",Msg::kInfo) << setw(width) << left << setfill('=') << "" << "\n";
00361 MSG("NuCut",Msg::kInfo) << setw(lsize) << left << setfill(' ') << "Total Events" << " " << setw(8) << right << fEventCount << " 100.00%\n";
00362 for (UInt_t i = 0; i < fCutTotals.size(); ++i)
00363 {
00364
00365 MSG("NuCut",Msg::kInfo)
00366 << setw(lsize) << left << fCutTotals[i].first
00367 << " " << setw(8) << right << fCutTotals[i].second
00368 << " " << setw(7) << right << fixed << setprecision(2) << fCutTotals[i].second*100./fEventCount << "%\n";
00369 }
00370 MSG("NuCut",Msg::kInfo) << endl;
00371 }
00372
00374
00375 Int_t NuCut::AnaVersionHash(const TString name)
00376 {
00377 TString upper(name);
00378 name.Hash();
00379 upper.ToUpper();
00380 Int_t hash = upper.Hash();
00381
00382
00383 if (hash > 0) hash *= -1;
00384
00385 return hash;
00386 }