22 #include "art/Framework/Core/EDAnalyzer.h"
23 #include "art/Framework/Core/ModuleMacros.h"
24 #include "art/Framework/Principal/Event.h"
25 #include "art_root_io/TFileService.h"
26 #include "cetlib_except/exception.h"
27 #include "messagefacility/MessageLogger/MessageLogger.h"
43 bdist(
const TVector3& pos,
unsigned int = 0,
unsigned int = 0)
47 art::ServiceHandle<geo::Geometry const> geom;
50 double d2 = 2. * geom->DetHalfWidth() - pos.X();
51 double d3 = pos.Y() + geom->DetHalfHeight();
52 double d4 = geom->DetHalfHeight() - pos.Y();
54 double d6 = geom->DetLength() - pos.Z();
56 return std::min({d1, d2, d3, d4, d5, d6});
74 double mctime = mctrk.
Start().
T();
81 int ntraj = mctrk.size();
82 for (
int itraj = 0; itraj < ntraj; ++itraj) {
83 const TLorentzVector& vec = mctrk[itraj].Position();
84 double dx = pos[0] - vec.X() - mcdx;
85 double dy = pos[1] - vec.Y();
86 double dz = pos[2] - vec.Z();
87 double dist = std::sqrt(dx * dx + dy * dy + dz * dz);
88 if (best_traj < 0 || dist < max_dist) {
113 art::ServiceHandle<geo::Geometry const> geom;
118 double xmax = 2. * geom->DetHalfWidth();
119 double ymin = -geom->DetHalfHeight();
120 double ymax = geom->DetHalfHeight();
122 double zmax = geom->DetLength();
125 int n = mctrk.size();
128 for (
int i = 0; i <
n; ++i) {
129 TVector3 pos = mctrk[i].Position().Vect();
135 if (pos.X() >= xmin && pos.X() <= xmax && pos.Y() >= ymin && pos.Y() <= ymax &&
136 pos.Z() >= zmin && pos.Z() <= zmax) {
142 startmom = 0.001 * mctrk[i].Momentum().Vect();
146 result += disp.Mag();
151 endmom = 0.001 * mctrk[i].Momentum().Vect();
162 effcalc(
const TH1* hnum,
const TH1* hden, TH1* heff)
164 int nbins = hnum->GetNbinsX();
165 if (nbins != hden->GetNbinsX())
166 throw cet::exception(
"SeedAna") <<
"effcalc[" __FILE__
"]: incompatible histograms (I)\n";
167 if (nbins != heff->GetNbinsX())
168 throw cet::exception(
"SeedAna") <<
"effcalc[" __FILE__
"]: incompatible histograms (II)\n";
172 for (
int ibin = 0; ibin <= nbins + 1; ++ibin) {
173 double num = hnum->GetBinContent(ibin);
174 double den = hden->GetBinContent(ibin);
176 heff->SetBinContent(ibin, 0.);
177 heff->SetBinError(ibin, 0.);
180 double eff = num / den;
181 if (eff < 0.) eff = 0.;
182 if (eff > 1.) eff = 1.;
183 double err = std::sqrt(eff * (1. - eff) / den);
184 heff->SetBinContent(ibin, eff);
185 heff->SetBinError(ibin, err);
189 heff->SetMinimum(0.);
190 heff->SetMaximum(1.05);
191 heff->SetMarkerStyle(20);
197 mulcalc(
const TH1* hnum,
const TH1* hden, TH1* hmul)
199 int nbins = hnum->GetNbinsX();
200 if (nbins != hden->GetNbinsX())
201 throw cet::exception(
"SeedAna") <<
"mulcalc[" __FILE__
"]: incompatible histograms (I)\n";
202 if (nbins != hmul->GetNbinsX())
203 throw cet::exception(
"SeedAna") <<
"mulcalc[" __FILE__
"]: incompatible histograms (II)\n";
207 for (
int ibin = 0; ibin <= nbins + 1; ++ibin) {
208 double num = hnum->GetBinContent(ibin);
209 double den = hden->GetBinContent(ibin);
211 hmul->SetBinContent(ibin, 0.);
212 hmul->SetBinError(ibin, 0.);
215 double mul = num / den;
216 if (mul < 0.) mul = 0.;
217 double err = std::sqrt((1. + mul) * mul / den);
218 hmul->SetBinContent(ibin, mul);
219 hmul->SetBinError(ibin, err);
223 hmul->SetMinimum(0.);
224 hmul->SetMarkerStyle(20);
254 MCHists(
const std::string& subdir);
342 explicit SeedAna(fhicl::ParameterSet
const& pset);
380 art::ServiceHandle<geo::Geometry const> geom;
381 art::ServiceHandle<art::TFileService>
tfs;
385 art::TFileDirectory topdir = tfs->mkdir(
"seedana",
"SeedAna histograms");
386 art::TFileDirectory
dir = topdir.mkdir(subdir);
391 dir.make<TH1F>(
"x",
"X Position", 100, -2. * geom->DetHalfWidth(), 4. * geom->DetHalfWidth());
392 fHy = dir.make<TH1F>(
"y",
"Y Position", 100, -geom->DetHalfHeight(), geom->DetHalfHeight());
393 fHz = dir.make<TH1F>(
"z",
"Z Position", 100, 0., geom->DetLength());
395 dir.make<TH1F>(
"dist",
"Position Distance to Boundary", 100, -10., geom->DetHalfWidth());
396 fHtheta = dir.make<TH1F>(
"theta",
"Theta", 100, 0., 3.142);
397 fHphi = dir.make<TH1F>(
"phi",
"Phi", 100, -3.142, 3.142);
398 fHtheta_xz = dir.make<TH1F>(
"theta_xz",
"Theta_xz", 100, -3.142, 3.142);
399 fHtheta_yz = dir.make<TH1F>(
"theta_yz",
"Theta_yz", 100, -3.142, 3.142);
411 art::ServiceHandle<geo::Geometry const> geom;
412 art::ServiceHandle<art::TFileService>
tfs;
416 art::TFileDirectory topdir = tfs->mkdir(
"seedana",
"SeedAna histograms");
417 art::TFileDirectory
dir = topdir.mkdir(subdir);
422 dir.make<TH2F>(
"duvcosth",
"Delta(uv) vs. Colinearity", 100, 0.95, 1., 100, 0., 1.);
423 fHcosth = dir.make<TH1F>(
"colin",
"Colinearity", 100, 0.95, 1.);
424 fHmcu = dir.make<TH1F>(
"mcu",
"MC Truth U", 100, -5., 5.);
425 fHmcv = dir.make<TH1F>(
"mcv",
"MC Truth V", 100, -5., 5.);
426 fHmcw = dir.make<TH1F>(
"mcw",
"MC Truth W", 100, -20., 20.);
427 fHmcdudw = dir.make<TH1F>(
"mcdudw",
"MC Truth U Slope", 100, -0.2, 0.2);
428 fHmcdvdw = dir.make<TH1F>(
"mcdvdw",
"MV Truth V Slope", 100, -0.2, 0.2);
431 "mcxstart",
"MC X Start Position", 10, -2. * geom->DetHalfWidth(), 4. * geom->DetHalfWidth());
433 "mcystart",
"MC Y Start Position", 10, -geom->DetHalfHeight(), geom->DetHalfHeight());
434 fHmcstartz = dir.make<TH1F>(
"mczstart",
"MC Z Start Position", 10, 0., geom->DetLength());
436 "mcxend",
"MC X End Position", 10, -2. * geom->DetHalfWidth(), 4. * geom->DetHalfWidth());
438 "mcyend",
"MC Y End Position", 10, -geom->DetHalfHeight(), geom->DetHalfHeight());
439 fHmcendz = dir.make<TH1F>(
"mczend",
"MC Z End Position", 10, 0., geom->DetLength());
440 fHmctheta = dir.make<TH1F>(
"mctheta",
"MC Theta", 20, 0., 3.142);
441 fHmcphi = dir.make<TH1F>(
"mcphi",
"MC Phi", 10, -3.142, 3.142);
442 fHmctheta_xz = dir.make<TH1F>(
"mctheta_xz",
"MC Theta_xz", 40, -3.142, 3.142);
443 fHmctheta_yz = dir.make<TH1F>(
"mctheta_yz",
"MC Theta_yz", 40, -3.142, 3.142);
444 fHmcmom = dir.make<TH1F>(
"mcmom",
"MC Momentum", 10, 0., 10.);
445 fHmclen = dir.make<TH1F>(
"mclen",
"MC Particle Length", 10, 0., 1.1 * geom->DetLength());
448 "Matched X Start Position",
450 -2. * geom->DetHalfWidth(),
451 4. * geom->DetHalfWidth());
453 "mystart",
"Matched Y Start Position", 10, -geom->DetHalfHeight(), geom->DetHalfHeight());
454 fHmstartz = dir.make<TH1F>(
"mzstart",
"Matched Z Start Position", 10, 0., geom->DetLength());
456 "mxend",
"Matched X End Position", 10, -2. * geom->DetHalfWidth(), 4. * geom->DetHalfWidth());
458 "myend",
"Matched Y End Position", 10, -geom->DetHalfHeight(), geom->DetHalfHeight());
459 fHmendz = dir.make<TH1F>(
"mzend",
"Matched Z End Position", 10, 0., geom->DetLength());
460 fHmtheta = dir.make<TH1F>(
"mtheta",
"Matched Theta", 20, 0., 3.142);
461 fHmphi = dir.make<TH1F>(
"mphi",
"Matched Phi", 10, -3.142, 3.142);
462 fHmtheta_xz = dir.make<TH1F>(
"mtheta_xz",
"Matched Theta_xz", 40, -3.142, 3.142);
463 fHmtheta_yz = dir.make<TH1F>(
"mtheta_yz",
"Matched Theta_yz", 40, -3.142, 3.142);
464 fHmmom = dir.make<TH1F>(
"mmom",
"Matched Momentum", 10, 0., 10.);
465 fHmlen = dir.make<TH1F>(
"mlen",
"Matched Particle Length", 10, 0., 1.1 * geom->DetLength());
468 "Good X Start Position",
470 -2. * geom->DetHalfWidth(),
471 4. * geom->DetHalfWidth());
473 "gystart",
"Good Y Start Position", 10, -geom->DetHalfHeight(), geom->DetHalfHeight());
474 fHgstartz = dir.make<TH1F>(
"gzstart",
"Good Z Start Position", 10, 0., geom->DetLength());
476 "gxend",
"Good X End Position", 10, -2. * geom->DetHalfWidth(), 4. * geom->DetHalfWidth());
478 "gyend",
"Good Y End Position", 10, -geom->DetHalfHeight(), geom->DetHalfHeight());
479 fHgendz = dir.make<TH1F>(
"gzend",
"Good Z End Position", 10, 0., geom->DetLength());
480 fHgtheta = dir.make<TH1F>(
"gtheta",
"Good Theta", 20, 0., 3.142);
481 fHgphi = dir.make<TH1F>(
"gphi",
"Good Phi", 10, -3.142, 3.142);
482 fHgtheta_xz = dir.make<TH1F>(
"gtheta_xz",
"Good Theta_xz", 40, -3.142, 3.142);
483 fHgtheta_yz = dir.make<TH1F>(
"gtheta_yz",
"Good Theta_yz", 40, -3.142, 3.142);
484 fHgmom = dir.make<TH1F>(
"gmom",
"Good Momentum", 10, 0., 10.);
485 fHglen = dir.make<TH1F>(
"glen",
"Good Particle Length", 10, 0., 1.1 * geom->DetLength());
488 "Multiplicity vs. X Start Position",
490 -2. * geom->DetHalfWidth(),
491 4. * geom->DetHalfWidth());
493 "Multiplicity vs. Y Start Position",
495 -geom->DetHalfHeight(),
496 geom->DetHalfHeight());
498 dir.make<TH1F>(
"mulzstart",
"Multiplicity vs. Z Start Position", 10, 0., geom->DetLength());
500 "Multiplicity vs. X End Position",
502 -2. * geom->DetHalfWidth(),
503 4. * geom->DetHalfWidth());
505 "Multiplicity vs. Y End Position",
507 -geom->DetHalfHeight(),
508 geom->DetHalfHeight());
510 dir.make<TH1F>(
"mulzend",
"Multiplicity vs. Z End Position", 10, 0., geom->DetLength());
511 fHmultheta = dir.make<TH1F>(
"multheta",
"Multiplicity vs. Theta", 20, 0., 3.142);
512 fHmulphi = dir.make<TH1F>(
"mulphi",
"Multiplicity vs. Phi", 10, -3.142, 3.142);
513 fHmultheta_xz = dir.make<TH1F>(
"multheta_xz",
"Multiplicity vs. Theta_xz", 40, -3.142, 3.142);
514 fHmultheta_yz = dir.make<TH1F>(
"multheta_yz",
"Multiplicity vs. Theta_yz", 40, -3.142, 3.142);
515 fHmulmom = dir.make<TH1F>(
"mulmom",
"Multiplicity vs. Momentum", 10, 0., 10.);
517 dir.make<TH1F>(
"mullen",
"Multiplicity vs. Particle Length", 10, 0., 1.1 * geom->DetLength());
520 "Efficiency vs. X Start Position",
522 -2. * geom->DetHalfWidth(),
523 4. * geom->DetHalfWidth());
525 "Efficiency vs. Y Start Position",
527 -geom->DetHalfHeight(),
528 geom->DetHalfHeight());
530 dir.make<TH1F>(
"ezstart",
"Efficiency vs. Z Start Position", 10, 0., geom->DetLength());
531 fHeendx = dir.make<TH1F>(
"exend",
532 "Efficiency vs. X End Position",
534 -2. * geom->DetHalfWidth(),
535 4. * geom->DetHalfWidth());
537 "eyend",
"Efficiency vs. Y End Position", 10, -geom->DetHalfHeight(), geom->DetHalfHeight());
538 fHeendz = dir.make<TH1F>(
"ezend",
"Efficiency vs. Z End Position", 10, 0., geom->DetLength());
539 fHetheta = dir.make<TH1F>(
"etheta",
"Efficiency vs. Theta", 20, 0., 3.142);
540 fHephi = dir.make<TH1F>(
"ephi",
"Efficiency vs. Phi", 10, -3.142, 3.142);
541 fHetheta_xz = dir.make<TH1F>(
"etheta_xz",
"Efficiency vs. Theta_xz", 40, -3.142, 3.142);
542 fHetheta_yz = dir.make<TH1F>(
"etheta_yz",
"Efficiency vs. Theta_yz", 40, -3.142, 3.142);
543 fHemom = dir.make<TH1F>(
"emom",
"Efficiency vs. Momentum", 10, 0., 10.);
545 dir.make<TH1F>(
"elen",
"Efficiency vs. Particle Length", 10, 0., 1.1 * geom->DetLength());
565 mf::LogInfo(
"SeedAna") <<
"SeedAna configured with the following parameters:\n"
568 <<
" Dump = " <<
fDump <<
"\n"
569 <<
" MinMCKE = " <<
fMinMCKE <<
"\n"
585 std::unique_ptr<mf::LogInfo> pdump;
588 pdump = std::unique_ptr<mf::LogInfo>(
new mf::LogInfo(
"TrackAna"));
593 bool mc = !evt.isRealData();
597 art::Handle<std::vector<recob::Seed>> seedh;
602 std::map<const recob::Seed*, int> seedmap;
608 art::Handle<std::vector<sim::MCTrack>> mctrackh;
614 *pdump <<
"MC Tracks\n"
615 <<
" Id pdg x y z dx dy dz "
617 <<
"--------------------------------------------------------------------------------"
624 art::ServiceHandle<detinfo::DetectorPropertiesService const>()->DataFor(evt);
626 for (std::vector<sim::MCTrack>::const_iterator imctrk = mctrackh->begin();
627 imctrk != mctrackh->end();
647 double mctime = mctrk.
Start().
T();
656 double plen = length(detProp, mctrk, mcdx, mcstart, mcend, mcstartmom, mcendmom);
666 double pstart = mcstartmom.Mag();
667 double pend = mcendmom.Mag();
668 *pdump <<
"\nOffset" << std::setw(3) << mctrk.
TrackID() << std::setw(6)
669 << mctrk.
PdgCode() <<
" " << std::fixed << std::setprecision(2)
670 << std::setw(10) << mcdx <<
"\nStart " << std::setw(3) << mctrk.
TrackID()
671 << std::setw(6) << mctrk.
PdgCode() <<
" " << std::fixed
672 << std::setprecision(2) << std::setw(10) << mcstart[0] << std::setw(10)
673 << mcstart[1] << std::setw(10) << mcstart[2];
675 *pdump <<
" " << std::fixed << std::setprecision(3) << std::setw(10)
676 << mcstartmom[0] / pstart << std::setw(10) << mcstartmom[1] / pstart
677 << std::setw(10) << mcstartmom[2] / pstart;
680 *pdump << std::setw(32) <<
" ";
681 *pdump << std::setw(12) << std::fixed << std::setprecision(3) << pstart;
682 *pdump <<
"\nEnd " << std::setw(3) << mctrk.
TrackID() << std::setw(6)
683 << mctrk.
PdgCode() <<
" " << std::fixed << std::setprecision(2)
684 << std::setw(10) << mcend[0] << std::setw(10) << mcend[1] << std::setw(10)
687 *pdump <<
" " << std::fixed << std::setprecision(3) << std::setw(10)
688 << mcendmom[0] / pend << std::setw(10) << mcendmom[1] / pend
689 << std::setw(10) << mcendmom[2] / pend;
692 *pdump << std::setw(32) <<
" ";
693 *pdump << std::setw(12) << std::fixed << std::setprecision(3) << pend <<
"\n";
699 std::ostringstream ostr;
705 double mctheta_xz = std::atan2(mcstartmom.X(), mcstartmom.Z());
706 double mctheta_yz = std::atan2(mcstartmom.Y(), mcstartmom.Z());
714 mchists.
fHmctheta->Fill(mcstartmom.Theta());
715 mchists.
fHmcphi->Fill(mcstartmom.Phi());
718 mchists.
fHmcmom->Fill(mcstartmom.Mag());
724 if (seedh.isValid()) {
728 int nseed = seedh->size();
729 for (
int i = 0; i < nseed; ++i) {
730 art::Ptr<recob::Seed> pseed(seedh, i);
732 if (seedmap.count(&seed) == 0) seedmap[&seed] = -1;
746 double dirmag = dir.Mag();
747 double diryz = std::sqrt(dir.Y() * dir.Y() + dir.Z() * dir.Z());
749 double sinth = dir.X() / dirmag;
750 double costh = diryz / dirmag;
754 sinphi = -dir.Y() / diryz;
755 cosphi = dir.Z() / diryz;
760 rot(0, 1) = sinth * sinphi;
762 rot(2, 1) = -costh * sinphi;
763 rot(0, 2) = -sinth * cosphi;
765 rot(2, 2) = costh * cosphi;
769 int itraj = mcmatch(detProp, mctrk, seed);
774 TVector3 mcpos = mctrk[itraj].Position().Vect() - pos;
775 TVector3 mcmom = mctrk[itraj].Momentum().Vect();
781 TVector3 mcmoml = rot * mcmom;
782 TVector3 mcposl = rot * mcpos;
784 if (mcmoml.Z() < 0.) mcmoml = -mcmoml;
785 double costh = mcmoml.Z() / mcmoml.Mag();
787 double u = mcposl.X();
788 double v = mcposl.Y();
789 double w = mcposl.Z();
791 double pu = mcmoml.X();
792 double pv = mcmoml.Y();
793 double pw = mcmoml.Z();
795 double dudw = pu /
pw;
796 double dvdw = pv /
pw;
798 double u0 = u - w * dudw;
799 double v0 = v - w * dvdw;
800 double uv0 = std::sqrt(u0 * u0 + v0 * v0);
817 mchists.
fHmcu->Fill(u0);
818 mchists.
fHmcv->Fill(v0);
819 mchists.
fHmcw->Fill(w);
834 mchists.
fHmendx->Fill(mcend.X());
835 mchists.
fHmendy->Fill(mcend.Y());
836 mchists.
fHmendz->Fill(mcend.Z());
837 mchists.
fHmtheta->Fill(mcstartmom.Theta());
838 mchists.
fHmphi->Fill(mcstartmom.Phi());
841 mchists.
fHmmom->Fill(mcstartmom.Mag());
842 mchists.
fHmlen->Fill(plen);
855 mchists.
fHgendx->Fill(mcend.X());
856 mchists.
fHgendy->Fill(mcend.Y());
857 mchists.
fHgendz->Fill(mcend.Z());
858 mchists.
fHgtheta->Fill(mcstartmom.Theta());
859 mchists.
fHgphi->Fill(mcstartmom.Phi());
862 mchists.
fHgmom->Fill(mcstartmom.Mag());
863 mchists.
fHglen->Fill(plen);
874 if (seedh.isValid()) {
878 int nseed = seedh->size();
880 if (nseed > 0 && pdump != 0) {
881 *pdump <<
"\nReconstructed Seeds\n"
882 <<
" MCid x y z dx dy dz "
884 <<
"--------------------------------------------------------------------------------"
888 for (
int i = 0; i < nseed; ++i) {
889 art::Ptr<recob::Seed> pseed(seedh, i);
899 double mdir = dir.Mag();
900 if (mdir != 0.) { dir *= (1. / mdir); }
902 double dpos = bdist(pos);
903 double theta_xz = std::atan2(dir.X(), dir.Z());
904 double theta_yz = std::atan2(dir.Y(), dir.Z());
909 int mcid = seedmap[&
seed];
910 *pdump << std::setw(15) << mcid <<
" " << std::fixed << std::setprecision(2)
911 << std::setw(10) << pos[0] << std::setw(10) << pos[1] << std::setw(10) << pos[2]
912 <<
" " << std::fixed << std::setprecision(3) << std::setw(10) << dir[0]
913 << std::setw(10) << dir[1] << std::setw(10) << dir[2] <<
"\n";
921 rhists.
fHx->Fill(pos.X());
922 rhists.
fHy->Fill(pos.Y());
923 rhists.
fHz->Fill(pos.Z());
924 rhists.
fHdist->Fill(dpos);
941 mf::LogInfo(
"SeedAna") <<
"SeedAna statistics:\n"
942 <<
" Number of events = " << fNumEvent;
946 for (std::map<int, MCHists>::const_iterator i = fMCHistMap.begin(); i != fMCHistMap.end();
948 const MCHists& mchists = i->second;
964 for (std::map<int, MCHists>::const_iterator i = fMCHistMap.begin(); i != fMCHistMap.end();
966 const MCHists& mchists = i->second;
double std(const std::vector< short > &wf, const double ped_mean, size_t start, size_t nsample)
std::string fMCTrackModuleLabel
EResult err(const char *call)
void GetPoint(double *Pt, double *Err) const
std::string fSeedModuleLabel
unsigned int ReadOutWindowSize() const
tick ticks
Alias for common language habits.
MCHists(const std::string &subdir)
void analyze(const art::Event &evt) override
process_name pandoraGausCryo1 vertexChargeCryo1 vertexStubCryo1 xmin
auto end(FixedBins< T, C > const &) noexcept
double ConvertXToTicks(double X, int p, int t, int c) const
double DriftVelocity(double efield=0., double temperature=0.) const
cm/us
Class def header for mctrack data container.
std::map< int, RecoHists > fRecoHistMap
const TLorentzVector & Momentum() const
SeedAna(fhicl::ParameterSet const &pset)
std::map< int, MCHists > fMCHistMap
constexpr double dist(const TReal *x, const TReal *y, const unsigned int dimension)
const MCStep & Start() const
art::ServiceHandle< art::TFileService > tfs
unsigned int TrackID() const
void GetDirection(double *Dir, double *Err) const
art framework interface to geometry description
RecoHists(const std::string &subdir)