10 #include "tensorflow/core/public/session.h" 28 #include "CLHEP/Random/RandGauss.h" 38 if ((samples == 0) || inps.empty() || inps.front().empty() || inps.front().front().empty())
41 if ((samples == -1) || (samples > (
int)inps.size())) { samples = inps.
size(); }
43 std::vector< std::vector<float> > results;
44 for (
int i = 0; i < samples; ++i)
46 results.push_back(
Run(inps[i]));
59 if (
stat(fileName, &buffer) == 0) { fname_out = fileName; }
63 <<
"Could not find the model file " << fileName;
77 mf::LogInfo(
"KerasModelInterface") <<
"Keras model loaded.";
83 std::vector< std::vector< std::vector<float> > > inp3d;
84 inp3d.push_back(inp2d);
103 mf::LogInfo(
"TfModelInterface") <<
"TF model loaded.";
109 if ((samples == 0) || inps.empty() || inps.front().empty() || inps.front().front().empty())
112 if ((samples == -1) || (samples > (
long long int)inps.size())) { samples = inps.
size(); }
114 long long int rows = inps.front().size(), cols = inps.front().front().size();
116 tensorflow::Tensor _x(tensorflow::DT_FLOAT, tensorflow::TensorShape({ samples, rows, cols, 1 }));
117 auto input_map = _x.tensor<float, 4>();
118 for (
long long int s = 0;
s < samples; ++
s) {
119 const auto & sample = inps[
s];
120 for (
long long int r = 0;
r < rows; ++
r) {
121 const auto &
row = sample[
r];
122 for (
long long int c = 0;
c < cols; ++
c) {
123 input_map(
s,
r,
c, 0) =
row[
c];
134 long long int rows = inp2d.size(), cols = inp2d.front().size();
136 tensorflow::Tensor _x(tensorflow::DT_FLOAT, tensorflow::TensorShape({ 1, rows, cols, 1 }));
137 auto input_map = _x.tensor<float, 4>();
138 for (
long long int r = 0;
r < rows; ++
r) {
139 const auto &
row = inp2d[
r];
140 for (
long long int c = 0;
c < cols; ++
c) {
141 input_map(0,
r,
c, 0) =
row[
c];
145 auto out =
g->run(_x);
146 if (!out.empty())
return out.front();
147 else return std::vector<float>();
157 fPatchSizeW(config.PatchSizeW()), fPatchSizeD(config.PatchSizeD()),
158 fCurrentWireIdx(99999), fCurrentScaledDrift(99999)
177 mf::LogError(
"PointIdAlg") <<
"File name extension not supported.";
180 if (!
fNNet) {
throw cet::exception(
"nnet::PointIdAlg") <<
"Loading model from file failed."; }
205 mf::LogError(
"PointIdAlg") <<
"Patch buffering failed.";
212 if (!out.empty()) { result = out[outIdx]; }
215 mf::LogError(
"PointIdAlg") <<
"Problem with applying model to input.";
225 std::vector<float>
result;
229 mf::LogError(
"PointIdAlg") <<
"Patch buffering failed.";
238 mf::LogError(
"PointIdAlg") <<
"Problem with applying model to input.";
248 if (points.empty() || !
fNNet) {
return std::vector< std::vector<float> >(); }
250 std::vector< std::vector< std::vector<float> > > inps(
251 points.size(), std::vector< std::vector<float> >(
253 for (
size_t i = 0; i < points.size(); ++i)
255 unsigned int wire = points[i].first;
256 float drift = points[i].second;
274 if ((wire1 == wire2) && (sd1 == sd2))
279 if ((wire1 == wire2) && ((size_t)drift1 == (
size_t)drift2))
306 std::vector<float> flat;
313 flat.resize(
patch.size() *
patch.front().size());
315 for (
size_t w = 0, i = 0;
w <
patch.size(); ++
w)
317 auto const & wire =
patch[
w];
318 for (
size_t d = 0;
d < wire.size(); ++
d, ++i)
334 if ((wire >= marginW) && (wire <
fNWires - marginW) &&
335 (scaledDrift >= marginD) && (scaledDrift <
fNScaledDrifts - marginD))
return true;
346 fWireProducerLabel(config.WireLabel()),
347 fHitProducerLabel(config.HitLabel()),
348 fTrackModuleLabel(config.TrackLabel()),
349 fSimulationProducerLabel(config.SimulationLabel()),
350 fSaveVtxFlags(config.SaveVtxFlags()),
351 fAdcDelay(config.AdcDelayTicks()),
352 fEventsPerBin(100, 0)
384 std::vector<float>
const & edeps, std::vector<int>
const & pdgs,
size_t wireIdx)
386 if ((wireIdx >=
fWireDriftEdep.size()) || (edeps.size() != pdgs.size())) {
return false; }
398 size_t i0 = i * dstep;
399 size_t i1 = (i + 1) * dstep;
404 float max_edep = edeps[i0];
405 for (
size_t k = i0 + 1;
k < i1; ++
k)
419 best_pdg |= type_flags;
430 auto const* detprop = lar::providerFrom<detinfo::DetectorPropertiesService>();
432 wd.
Wire = 0; wd.Drift = 0; wd.TPC = -1; wd.Cryo = -1;
436 double vtx[3] = {tvec.X(), tvec.Y(), tvec.Z()};
440 unsigned int tpc = tpcid.
TPC, cryo = tpcid.
Cryostat;
443 float dx = tvec.T() * 1.e-3 * detprop->DriftVelocity();
445 if (driftDir == 1) { dx *= -1; }
446 else if (driftDir != -1)
450 vtx[0] = tvec.X() + dx;
454 wd.TPC = tpc; wd.Cryo = cryo;
459 mf::LogWarning(
"TrainingDataAlg") <<
"Vertex projection out of wire planes, just skipping this vertex.";
463 mf::LogWarning(
"TrainingDataAlg") <<
"Vertex projection out of wire planes, skip MC vertex.";
470 const std::unordered_map< int, const simb::MCParticle* > & particleMap)
const 472 const float minElectronLength2 = 2.5*2.5;
473 const float maxDeltaLength2 = 0.15*0.15;
476 if (pdg != 11)
return false;
479 for (
size_t d = 0;
d < nSec; ++
d)
481 auto d_search = particleMap.find(particle.
Daughter(
d));
482 if (d_search != particleMap.end())
484 auto const & daughter = *((*d_search).second);
485 int d_pdg =
abs(daughter.PdgCode());
486 if (d_pdg != 22) {
return false; }
490 float trkLength2 = 0;
491 auto const *
p = &particle;
492 bool branching =
false;
496 auto m_search = particleMap.find(
p->Mother());
497 if (m_search != particleMap.end())
499 p = (*m_search).second;
500 int m_pdg =
abs(
p->PdgCode());
503 nSec =
p->NumberDaughters();
505 for (
size_t d = 0;
d < nSec; ++
d)
507 auto d_search = particleMap.find(
p->Daughter(
d));
508 if (d_search != particleMap.end())
510 auto const & daughter = *((*d_search).second);
511 int d_pdg =
abs(daughter.PdgCode());
518 if (ne > 1) { branching =
true; }
525 return (trkLength2 > minElectronLength2);
529 const std::unordered_map< int, const simb::MCParticle* > & particleMap)
const 531 bool hasElectron =
false, hasNuMu =
false, hasNuE =
false;
534 if ((pdg == 13) && (particle.
EndProcess() ==
"FastScintillation"))
537 for (
size_t d = 0;
d < nSec; ++
d)
539 auto d_search = particleMap.find(particle.
Daughter(
d));
540 if (d_search != particleMap.end())
542 auto const & daughter = *((*d_search).second);
543 int d_pdg =
abs(daughter.PdgCode());
544 if (d_pdg == 11) hasElectron =
true;
545 else if (d_pdg == 14) hasNuMu =
true;
546 else if (d_pdg == 12) hasNuE =
true;
551 return (hasElectron && hasNuMu && hasNuE);
555 std::unordered_map<
size_t, std::unordered_map< int, int > > & wireToDriftToVtxFlags,
556 const std::unordered_map< int, const simb::MCParticle* > & particleMap,
557 unsigned int plane)
const 559 for (
auto const &
p : particleMap)
561 auto const & particle = *
p.second;
563 double ekStart = 1000. * (particle.E() - particle.Mass());
564 double ekEnd = 1000. * (particle.EndE() - particle.Mass());
566 int pdg =
abs(particle.PdgCode());
573 if ((particle.EndProcess() ==
"conv") &&
607 if (particle.Mother() != 0)
609 auto search = particleMap.find(particle.Mother());
610 if (
search != particleMap.end())
612 auto const & mother = *((*search).second);
613 int m_pdg =
abs(mother.PdgCode());
614 unsigned int nSec = mother.NumberDaughters();
615 unsigned int nVisible = 0;
618 for (
size_t d = 0;
d < nSec; ++
d)
620 auto d_search = particleMap.find(mother.Daughter(
d));
621 if (d_search != particleMap.end())
623 auto const & daughter = *((*d_search).second);
624 int d_pdg =
abs(daughter.PdgCode());
625 if (((d_pdg == 2212) || (d_pdg == 211) || (d_pdg == 321)) &&
626 (1000. * (daughter.E() - daughter.Mass()) > 50.0))
636 if (((m_pdg != pdg) && (m_pdg != 2112)) || ((m_pdg != 2112) && (nVisible > 0)) || ((m_pdg == 2112) && (nVisible > 1)))
647 if (particle.EndProcess() ==
"FastScintillation")
649 unsigned int nSec = particle.NumberDaughters();
650 for (
size_t d = 0;
d < nSec; ++
d)
652 auto d_search = particleMap.find(particle.Daughter(
d));
653 if (d_search != particleMap.end())
655 auto const & daughter = *((*d_search).second);
656 int d_pdg =
abs(daughter.PdgCode());
657 if ((pdg == 321) && (d_pdg == 13))
663 if ((pdg == 211) && (d_pdg == 13))
673 if ((particle.EndProcess() ==
"Decay") && (ekEnd > 200.0))
675 unsigned int nSec = particle.NumberDaughters();
676 for (
size_t d = 0;
d < nSec; ++
d)
678 auto d_search = particleMap.find(particle.Daughter(
d));
679 if (d_search != particleMap.end())
681 auto const & daughter = *((*d_search).second);
682 int d_pdg =
abs(daughter.PdgCode());
683 if ((pdg == 321) && (d_pdg == 13))
689 if ((pdg == 211) && (d_pdg == 13))
704 if (particle.Process() ==
"primary")
716 wireToDriftToVtxFlags[wd.Wire][wd.Drift] |= flagsStart;
727 wireToDriftToVtxFlags[wd.Wire][wd.Drift] |= flagsEnd;
741 if (pdg == 321 || pdg == 211 || pdg == 2212){
744 if (thisTrajectoryProcessMap1.size()){
745 for(
auto const& couple1: thisTrajectoryProcessMap1){
746 if ((truetraj.
KeyToProcess(couple1.second)).find(
"Elastic")!= std::string::npos){
752 if ((truetraj.
KeyToProcess(couple1.second)).find(
"Inelastic")!= std::string::npos){
766 unsigned int plane,
unsigned int tpc,
unsigned int cryo)
770 std::vector< art::Ptr<recob::Wire> > Wirelist;
776 mf::LogError(
"TrainingDataAlg") <<
"Wire data not set.";
782 std::vector< art::Ptr<recob::Hit> > Hitlist;
789 std::vector< art::Ptr<recob::Track> > Tracklist;
797 for (
size_t widx = 0; widx < 240; ++widx) {
799 std::vector< float > labels_deposit(
fNDrifts, 0);
800 std::vector< int > labels_pdg(
fNDrifts, 0);
803 for(
size_t subwidx = 0; subwidx < Wirelist.size(); ++subwidx) {
804 if(widx+240 == Wirelist[subwidx]->
Channel()) {
805 labels_deposit = Wirelist[subwidx]->Signal();
821 for(
size_t iHit = 0; iHit < Hitlist.size(); ++iHit) {
823 if(Hitlist[iHit]->
Channel() != widx+240) {
continue; }
824 if(Hitlist[iHit]->
View() != 1) {
continue; }
827 if(ass_trk_hits.at(iHit).size() == 0) {
continue; }
832 if(ass_trk_hits.at(iHit)[0]->Length() < 5) {
continue; }
838 for(
size_t jHit = 0; jHit < Hitlist.size(); ++jHit) {
839 if(jHit == iHit) {
continue; }
840 if(Hitlist[jHit]->
View() != 1) {
continue; }
842 if(ass_trk_hits.at(jHit).size() == 0) {
continue; }
843 if(ass_trk_hits.at(jHit)[0]->ID() !=
844 ass_trk_hits.at(iHit)[0]->ID()) {
continue; }
846 double dist = sqrt((Hitlist[iHit]->
Channel()-Hitlist[jHit]->
Channel()) *
848 (Hitlist[iHit]->PeakTime()-Hitlist[jHit]->PeakTime()) *
849 (Hitlist[iHit]->PeakTime()-Hitlist[jHit]->PeakTime()));
861 for(
size_t jHit = 0; jHit < Hitlist.size(); ++jHit) {
862 if(jHit == iHit or
int(jHit) == far_index) {
continue; }
863 if(Hitlist[jHit]->
View() != 1) {
continue; }
865 if(ass_trk_hits.at(jHit).size() == 0) {
continue; }
866 if(ass_trk_hits.at(jHit)[0]->ID() !=
867 ass_trk_hits.at(iHit)[0]->ID()) {
continue; }
869 double dist = sqrt((Hitlist[far_index]->
Channel()-Hitlist[jHit]->
Channel()) *
871 (Hitlist[far_index]->PeakTime()-Hitlist[jHit]->PeakTime()) *
872 (Hitlist[far_index]->PeakTime()-Hitlist[jHit]->PeakTime()));
874 if(other_dist < dist){
881 double del_wire = double(Hitlist[other_end]->
Channel() - Hitlist[far_index]->
Channel());
882 double del_time = double(Hitlist[other_end]->PeakTime() - Hitlist[far_index]->PeakTime());
883 double hypo = sqrt(del_wire * del_wire + del_time * del_time);
885 if(hypo == 0) {
continue; }
887 double cosser = TMath::Abs(del_wire / hypo);
888 double norm_ang = TMath::ACos(cosser) * 2 / TMath::Pi();
900 labels_pdg[Hitlist[iHit]->PeakTime()] = 211;
919 unsigned int plane,
unsigned int tpc,
unsigned int cryo)
926 mf::LogError(
"TrainingDataAlg") <<
"Wire data not set.";
932 mf::LogInfo(
"TrainingDataAlg") <<
"Skip MC simulation info.";
943 std::unordered_map< int, const simb::MCParticle* > particleMap;
944 for (
auto const & particle : *particleHandle)
946 particleMap[particle.TrackId()] = &particle;
949 std::unordered_map< size_t, std::unordered_map< int, int > > wireToDriftToVtxFlags;
954 std::map< int, int > trackToPDG;
955 for (
size_t widx = 0; widx <
fNWires; ++widx)
960 std::vector< float > labels_deposit(
fNDrifts, 0);
961 std::vector< int > labels_pdg(labels_deposit.size(), 0);
962 int labels_size = labels_deposit.size();
964 std::map< int, std::map< int, double > > timeToTrackToCharge;
965 for (
auto const &
channel : *simChannelHandle)
967 if (
channel.Channel() != wireChannelNumber)
continue;
969 auto const & timeSlices =
channel.TDCIDEMap();
970 for (
auto const & timeSlice : timeSlices)
972 int time = timeSlice.first;
974 auto const & energyDeposits = timeSlice.second;
975 for (
auto const & energyDeposit : energyDeposits)
978 int tid = energyDeposit.trackID;
981 pdg = 11; tid = -tid;
983 auto search = particleMap.find(tid);
984 if (
search == particleMap.end())
989 auto const & mother = *((*search).second);
990 int mPdg =
abs(mother.PdgCode());
991 if ((mPdg == 13) || (mPdg == 211) || (mPdg == 2212))
998 auto search = particleMap.find(tid);
999 if (
search == particleMap.end())
1004 auto const & particle = *((*search).second);
1005 pdg =
abs(particle.PdgCode());
1007 if (particle.Process() ==
"primary")
1019 auto msearch = particleMap.find(particle.Mother());
1020 if (msearch != particleMap.end())
1022 auto const & mother = *((*msearch).second);
1033 trackToPDG[energyDeposit.trackID] =
pdg;
1035 double energy = energyDeposit.numElectrons * electronsToGeV;
1036 timeToTrackToCharge[time][energyDeposit.trackID] +=
energy;
1044 for (
auto const & ttc : timeToTrackToCharge)
1046 float max_deposit = 0.0;
1048 for (
auto const & tc : ttc.second) {
1050 if( tc.second > max_deposit )
1052 max_deposit = tc.second;
1053 max_pdg = trackToPDG[tc.first];
1057 if (ttc.first < labels_size)
1060 if (tick_idx < labels_size)
1062 labels_deposit[tick_idx] = max_deposit;
1063 labels_pdg[tick_idx] = max_pdg & type_pdg_mask;
1068 for (
auto const & drift_flags : wireToDriftToVtxFlags[widx])
1070 int drift = drift_flags.first, flags = drift_flags.second;
1071 if ((drift >= 0) && (drift < labels_size))
1073 labels_pdg[drift] |= flags;
1089 float max_cut = 0.25 * max_e_cut;
1096 if (cut < max_cut) w0++;
1104 if (cut < max_cut) w1--;
1114 if (cut < max_cut) d0++;
1122 if (cut < max_cut) d1--;
1127 unsigned int margin = 20;
1128 if ((w1 - w0 > 8) && (d1 - d0 > 8))
1130 if (w0 < margin) w0 = 0;
1136 if (d0 < margin) d0 = 0;
bool isInsideFiducialRegion(unsigned int wire, float drift) const
virtual void resizeView(size_t wires, size_t drifts)
Store parameters for running LArG4.
geo::GeometryCore const * fGeometry
bool bufferPatch(size_t wire, float drift, std::vector< std::vector< float > > &patch) const
void collectVtxFlags(std::unordered_map< size_t, std::unordered_map< int, int > > &wireToDriftToVtxFlags, const std::unordered_map< int, const simb::MCParticle * > &particleMap, unsigned int plane) const
bool setWireEdepsAndLabels(std::vector< float > const &edeps, std::vector< int > const &pdgs, size_t wireIdx)
std::vector< raw::ChannelID_t > fWireChannels
Utilities related to art service access.
bool isMuonDecaying(const simb::MCParticle &particle, const std::unordered_map< int, const simb::MCParticle * > &particleMap) const
std::vector< std::vector< float > > Run(std::vector< std::vector< std::vector< float > > > const &inps, int samples=-1) override
fhicl::Atom< std::string > NNetModelFile
std::vector< std::vector< int > > fWireDriftPdg
AdcChannelData::View View
MaybeLogger_< ELseverityLevel::ELsev_info, false > LogInfo
art::InputTag fTrackModuleLabel
const value_type & at(const size_type i) const
std::vector< std::vector< float > > fWireDriftPatch
bool isValid
Whether this ID points to a valid element.
std::string KeyToProcess(unsigned char const &key) const
static std::vector< float > flattenData2D(std::vector< std::vector< float > > const &patch)
virtual std::vector< float > Run(std::vector< std::vector< float > > const &inp2d)=0
virtual void set_data(std::vector< std::vector< std::vector< float > > > const &)
CryostatID_t Cryostat
Index of cryostat.
fhicl::Sequence< std::string > NNetOutputs
DataProviderAlg(const fhicl::ParameterSet &pset)
bool setEventData(const art::Event &event, unsigned int plane, unsigned int tpc, unsigned int cryo)
MaybeLogger_< ELseverityLevel::ELsev_error, false > LogError
std::vector< size_t > fEventsPerBin
std::vector< float > compute_output(keras::DataChunk *dc)
bool isCurrentPatch(unsigned int wire, float drift) const
int NumberDaughters() const
~TrainingDataAlg(void) override
std::vector< std::string > fNNetOutputs
bool setWireDriftData(const std::vector< recob::Wire > &wires, unsigned int plane, unsigned int tpc, unsigned int cryo)
nnet::ModelInterface * fNNet
int Daughter(const int i) const
virtual double ConvertXToTicks(double X, int p, int t, int c) const =0
art::InputTag fWireProducerLabel
geo::TPCID FindTPCAtPosition(double const worldLoc[3]) const
Returns the ID of the TPC at specified location.
~PointIdAlg(void) override
bool isElectronEnd(const simb::MCParticle &particle, const std::unordered_map< int, const simb::MCParticle * > &particleMap) const
std::vector< float > predictIdVector(unsigned int wire, float drift) const
calculate multi-class probabilities for [wire, drift] point
bool getByLabel(std::string const &label, std::string const &instance, Handle< PROD > &result) const
constexpr ChannelID_t InvalidChannelID
ID of an invalid channel.
std::string EndProcess() const
detinfo::DetectorProperties const * fDetProp
Collection of exceptions for Geometry system.
unsigned int fNCachedDrifts
geo::WireID::WireID_t NearestWire(geo::Point_t const &point, geo::PlaneID const &planeid) const
Returns the index of wire closest to position in the specified TPC.
std::vector< std::vector< float > > fWireDriftEdep
KerasModelInterface(const char *modelFileName)
bool findCrop(float max_e_cut, unsigned int &w0, unsigned int &w1, unsigned int &d0, unsigned int &d1) const
WireDrift getProjection(const TLorentzVector &tvec, unsigned int plane) const
The data type to uniquely identify a TPC.
ProcessMap const & TrajectoryProcesses() const
static std::unique_ptr< Graph > create(const char *graph_file_name, const std::vector< std::string > &outputs={}, int ninputs=1, int noutputs=1)
cet::coded_exception< errors::ErrorCodes, ExceptionDetail::translate > Exception
TfModelInterface(const char *modelFileName)
std::vector< float > Run(std::vector< std::vector< float > > const &inp2d) override
std::string findFile(const char *fileName) const
short int DetectDriftDirection() const
Returns the expected drift direction based on geometry.
std::vector< std::vector< float > > predictIdVectors(std::vector< std::pair< unsigned int, float > > points) const
unsigned int fNScaledDrifts
MaybeLogger_< ELseverityLevel::ELsev_warning, false > LogWarning
static float particleRange2(const simb::MCParticle &particle)
object containing MC truth information necessary for making RawDigits and doing back tracking ...
size_t fCurrentScaledDrift
std::string find_file(std::string const &filename) const
Interface for experiment-specific channel quality info provider.
TPCGeo const & TPC(unsigned int const tpc=0, unsigned int const cstat=0) const
Returns the specified TPC.
Exception thrown on invalid wire number (e.g. NearestWireID())
art::InputTag fSimulationProducerLabel
Interface to algorithm class for a specific detector channel mapping.
std::string fNNetModelFilePath
void fill_ptr_vector(std::vector< Ptr< T >> &ptrs, H const &h)
TPCID_t TPC
Index of the TPC within its cryostat.
Interface for experiment-specific service for channel quality info.
bool isSamePatch(unsigned int wire1, float drift1, unsigned int wire2, float drift2) const
test if two wire/drift coordinates point to the same patch
bool setDataEventData(const art::Event &event, unsigned int plane, unsigned int tpc, unsigned int cryo)
void resizeView(size_t wires, size_t drifts) override
art::InputTag fHitProducerLabel
double GeVToElectrons() const
cet::coded_exception< error, detail::translate > exception
QTextStream & endl(QTextStream &s)
Event finding and building.
TrainingDataAlg(const fhicl::ParameterSet &pset)
ChannelMappingService::Channel Channel
float predictIdValue(unsigned int wire, float drift, size_t outIdx=0) const
calculate single-value prediction (2-class probability) for [wire, drift] point
PointIdAlg(const fhicl::ParameterSet &pset)