2 #include <EVENT/LCRelation.h>
3 #include <EVENT/MCParticle.h>
4 #include <UTIL/LCRelationNavigator.h>
5 #include "marlin/Global.h"
6 #include "EVENT/LCCollection.h"
7 #include <ClusterShapes.h>
8 #include "EVENT/Track.h"
9 #include "IMPL/LCCollectionVec.h"
10 #include "IMPL/ReconstructedParticleImpl.h"
11 #include "IMPL/VertexImpl.h"
14 #include <DD4hep/Detector.h>
15 #include <DD4hep/DD4hepUnits.h>
16 #include <DDRec/DetectorData.h>
18 #include "HelixClass.h"
20 using namespace lcio ;
21 using namespace marlin ;
43 _description =
"Kink Finder Processor : finds kinks, prongs and splits" ;
45 registerInputCollection(LCIO::TRACK,
47 "Name of input collection of reconstructed particles",
49 std::string(
"LDCTracks"));
51 registerOutputCollection(LCIO::RECONSTRUCTEDPARTICLE,
52 "KinkRecoParticleCollection",
53 "Name of output collection of kink reconstructed particles",
55 std::string(
"KinkRecoParticles"));
57 registerOutputCollection(LCIO::VERTEX,
58 "KinkVertexCollection",
59 "Name of output collection of kink vertices",
61 std::string(
"KinkVertices"));
63 registerOutputCollection(LCIO::RECONSTRUCTEDPARTICLE,
64 "ProngRecoParticleCollection",
65 "Name of output collection of prong reconstructed particles",
67 std::string(
"ProngRecoParticles"));
69 registerOutputCollection(LCIO::VERTEX,
70 "ProngVertexCollection",
71 "Name of output collection of prong vertices",
73 std::string(
"ProngVertices"));
76 registerOutputCollection(LCIO::RECONSTRUCTEDPARTICLE,
77 "SplitRecoParticleCollection",
78 "Name of output collection of split reconstructed particles",
80 std::string(
"SplitRecoParticles"));
82 registerOutputCollection(LCIO::VERTEX,
83 "SplitVertexCollection",
84 "Name of output collection of split vertices",
86 std::string(
"SplitVertices"));
89 registerProcessorParameter(
"SplitTrackMaxFracDeltaP",
90 "Maximum fractional difference in deltaP for split tracks",
94 registerProcessorParameter(
"SplitTrackMaxDeltaP",
95 "Maximum difference in deltaP for split tracks",
99 registerProcessorParameter(
"CutOnRadius",
100 "Cuts on Kink radius",
104 registerProcessorParameter(
"MinimumTrackHits",
105 "cuts on number of track hits",
109 registerProcessorParameter(
"MaxDeltaTpcLayers",
110 "Cuts on Kink DeltaRxy for tracks in TPC",
115 registerProcessorParameter(
"PionDecayMassCut",
116 "Cuts on kink mass for pion decay",
120 registerProcessorParameter(
"KaonDecayMassCut",
121 "Cuts on kink mass for kaon decay",
125 registerProcessorParameter(
"SigmaDecayMassCut",
126 "Cuts on kink mass for sigma decay",
130 registerProcessorParameter(
"SigmaTimeCut",
131 "Cuts on lifetime for sigma decay",
135 registerProcessorParameter(
"HyperonDecayMassCut",
136 "Cuts on kink mass for hyperon decay",
140 registerProcessorParameter(
"HyperonTimeCut",
141 "Cuts on lifetime for hyperon decay",
145 registerProcessorParameter(
"KinkProjectionCutTPC",
146 "Cuts on kink distance of closest approach in TPC",
150 registerProcessorParameter(
"TightKinkProjectionCutTPC",
151 "Tight Cut on kink distance of closest approach in TPC",
155 registerProcessorParameter(
"VeryTightKinkProjectionCutTPC",
156 "Very Tight Cut on kink distance of closest approach in TPC",
160 registerProcessorParameter(
"KinkProjectionCutSIT",
161 "Cuts on kink distance of closest approach in SIT",
165 registerProcessorParameter(
"LooseProjectionCutSIT",
166 "Cuts on kink distance of closest approach in SIT",
170 registerProcessorParameter(
"MinELambda",
171 "Minimum Lambda Energy",
176 registerProcessorParameter(
"DebugPrinting",
189 dd4hep::Detector& theDet = dd4hep::Detector::getInstance();
192 theDet.field().magneticField( { 0., 0., 0. } , bfieldV ) ;
193 _bField = bfieldV[2]/dd4hep::tesla ;
195 dd4hep::DetElement tpcDE = theDet.detector(
"TPC") ;
196 const dd4hep::rec::FixedPadSizeTPCData* tpc = tpcDE.extension<dd4hep::rec::FixedPadSizeTPCData>() ;
204 dd4hep::DetElement vtxDE = theDet.detector(
"VXD");
205 dd4hep::rec::ZPlanarData* vtx = vtxDE.extension<dd4hep::rec::ZPlanarData>();
212 dd4hep::DetElement sitDE = theDet.detector(
"SIT");
213 dd4hep::rec::ZPlanarData* sit = sitDE.extension<dd4hep::rec::ZPlanarData>();
239 if(
_debugPrinting>0)std::cout <<
" Searching for kinks/prongs/split tracks " << std::endl;
242 LCCollection* relationTrackCollection = NULL;
243 LCRelationNavigator* trackNavigator=NULL;
245 relationTrackCollection = evt->getCollection(
"LDCTracksMCP");
246 trackNavigator =
new LCRelationNavigator(relationTrackCollection);
248 catch(DataNotAvailableException &
e){
252 LCCollection * col = evt->getCollection(
_trackColName.c_str() );
254 int nelem = col->getNumberOfElements();
255 TrackPairVec trkPairs;
257 std::map<Track*,int> trackUsed;
259 for (
int i=0;i<nelem;++i) {
260 Track * trk =
dynamic_cast<Track*
>(col->getElementAt(i));
261 tracks.push_back(trk);
265 catch(DataNotAvailableException &e) {}
267 std::vector<vec3>rin;
268 std::vector<vec3>rout;
269 std::vector<float>rOuter;
270 std::vector<float>rInner;
271 std::vector<vec3>zin;
272 std::vector<vec3>zout;
273 std::vector<float>momentum;
274 std::vector<float>momentumZ;
275 std::vector<float>momentumS;
276 std::vector<float>momentumE;
277 std::vector<float>charge;
278 std::vector<int>hits;
279 std::vector<MCParticle*>mcParticle;
280 std::vector<HelixClass*> helixEnd( tracks.size() );
281 std::vector<HelixClass*> helixStart(tracks.size() );
282 std::vector< std::vector<twoTrackIntersection_t> > kinkDaughters ( tracks.size() ) ;
283 std::vector< std::vector<twoTrackIntersection_t> > prongDaughters( tracks.size() ) ;
284 std::vector< std::vector<twoTrackIntersection_t> > splitDaughters( tracks.size() ) ;
285 std::vector< float> zAtEnd( tracks.size() );
286 std::vector< float> zAtStart(tracks.size() );
288 for(
unsigned int itrack=0;itrack< tracks.size();++itrack){
289 TrackerHitVec hitvec = tracks[itrack]->getTrackerHits();
290 int nhits = (int)hitvec.size();
291 hits.push_back(nhits);
293 float router =-99999.;
295 float rinner =99999.;
298 float abszmax =-99999.;
299 float abszmin =99999.;
302 for(
int ih =0;ih<nhits;++ih){
303 float x = (float)hitvec[ih]->getPosition()[0];
304 float y = (float)hitvec[ih]->getPosition()[1];
305 float z = (float)hitvec[ih]->getPosition()[2];
318 if(r<rinner && r>15.){
328 ri.
x = (float)hitvec[inner]->getPosition()[0];
329 ri.
y = (float)hitvec[inner]->getPosition()[1];
330 ri.
z = (float)hitvec[inner]->getPosition()[2];
333 ro.
x = (float)hitvec[outer]->getPosition()[0];
334 ro.
y = (float)hitvec[outer]->getPosition()[1];
335 ro.
z = (float)hitvec[outer]->getPosition()[2];
338 zi.
x = (float)hitvec[min]->getPosition()[0];
339 zi.
y = (float)hitvec[min]->getPosition()[1];
340 zi.
z = (float)hitvec[min]->getPosition()[2];
342 zo.
x = (float)hitvec[max]->getPosition()[0];
343 zo.
y = (float)hitvec[max]->getPosition()[1];
344 zo.
z = (float)hitvec[max]->getPosition()[2];
347 rInner.push_back(rinner);
348 rOuter.push_back(router);
350 if (fabs(zmin)<fabs(zmax)) {
357 float signPz = zEnd - zBegin;
358 zAtEnd[itrack] = zEnd;
359 zAtStart[itrack] = zBegin;
361 int _nHitsInFit = 50;
363 if (nhits > _nHitsInFit) {
364 for (
int iz = 0 ; iz < nhits-1; iz++)
365 for (
int jz = 0; jz < nhits-iz-1; jz++){
366 TrackerHit * one = hitvec[jz];
367 TrackerHit * two = hitvec[jz+1];
368 float dist1 = fabs(
float(one->getPosition()[2])-zBegin);
369 float dist2 = fabs(
float(two->getPosition()[2])-zBegin);
372 TrackerHit * Temp = hitvec[jz];
373 hitvec[jz] = hitvec[jz+1];
377 nhitsFit = _nHitsInFit;
383 float phi0 = tracks[itrack]->getPhi();
384 float d0 = tracks[itrack]->getD0();
385 float omega = tracks[itrack]->getOmega();
386 float z0 = tracks[itrack]->getZ0();
387 float tanlambda = tracks[itrack]->getTanLambda();
388 helix.Initialize_Canonical(phi0, d0, z0, omega, tanlambda,
_bField);
389 float totMomentum =0;
391 for (
int j=0; j < 3; ++j) {
392 Mom[j] = helix.getMomentum()[j];
393 totMomentum += Mom[j]*Mom[j];
395 totMomentum = sqrt(totMomentum);
396 momentum.push_back(totMomentum);
397 momentumZ.push_back(Mom[2]);
398 charge.push_back(helix.getCharge());
400 MCParticle* mcpart = NULL;
401 if(trackNavigator!=NULL){
402 LCObjectVec objectVec = trackNavigator->getRelatedToObjects(tracks[itrack]);
403 if (objectVec.size() > 0)mcpart = dynamic_cast<MCParticle*>(objectVec[0]);
404 if (objectVec.size() > 1){
405 float dbest = 999999999.;
406 for(
unsigned im=0;im<objectVec.size();im++ ){
407 MCParticle* mcparti =
dynamic_cast<MCParticle*
>(objectVec[im]);
410 p[0] = mcparti->getMomentum()[0];
411 p[1] = mcparti->getMomentum()[1];
412 p[2] = mcparti->getMomentum()[2];
413 float ptot = sqrt(p[0]*p[0]+p[1]*p[1]+p[2]*p[2]);
414 float d = fabs(ptot-totMomentum);
423 mcParticle.push_back(mcpart);
425 float * xh =
new float[nhitsFit];
426 float * yh =
new float[nhitsFit];
427 float * zh =
new float[nhitsFit];
428 float * ah =
new float[nhitsFit];
429 for (
int i=0; i<nhitsFit; ++i) {
431 xh[i] = float(hitvec[i]->getPosition()[0]);
432 yh[i] = float(hitvec[i]->getPosition()[1]);
433 zh[i] = float(hitvec[i]->getPosition()[2]);
436 ClusterShapes * shapesS =
new ClusterShapes(nhitsFit,ah,xh,yh,zh);
441 shapesS->FitHelix(500, 0, 1, par, dpar, chi2, distmax);
449 helixStart[itrack] =
new HelixClass();
450 helixStart[itrack]->Initialize_BZ(x0, y0, r0,
457 refs[0] = helixStart[itrack]->getReferencePoint()[0];
458 refs[1] = helixStart[itrack]->getReferencePoint()[1];
459 refs[2] = helixStart[itrack]->getReferencePoint()[2];
461 helixStart[itrack]->getPointInZ(zAtEnd[itrack], refs, seeds);
462 for (
int i=0; i<nhitsFit; ++i) {
464 xh[i] = float(hitvec[nhits-1-i]->getPosition()[0]);
465 yh[i] = float(hitvec[nhits-1-i]->getPosition()[1]);
466 zh[i] = float(hitvec[nhits-1-i]->getPosition()[2]);
468 ClusterShapes * shapesE =
new ClusterShapes(nhitsFit,ah,xh,yh,zh);
469 shapesE->FitHelix(500, 0, 1, par, dpar, chi2, distmax);
476 helixEnd[itrack] =
new HelixClass();
477 helixEnd[itrack]->Initialize_BZ(x0, y0, r0,
488 for(
unsigned int i=0;i< tracks.size();++i){
496 refe[0] = helixEnd[i]->getReferencePoint()[0];
497 refe[1] = helixEnd[i]->getReferencePoint()[1];
498 refe[2] = helixEnd[i]->getReferencePoint()[2];
499 helixEnd[i]->getPointInZ(z, refe, seedi);
500 float rendi = sqrt(seedi[0]*seedi[0]+seedi[1]*seedi[1]);
501 for(
unsigned int j=0;j< tracks.size();++j){
519 bool flipped =
false;
520 if(fabs(zAtEnd[i]-zAtStart[j])<=fabs(zAtEnd[i]-zAtEnd[j])){
524 refs[0] = helixStart[j]->getReferencePoint()[0];
525 refs[1] = helixStart[j]->getReferencePoint()[1];
526 refs[2] = helixStart[j]->getReferencePoint()[2];
527 helixStart[j]->getPointInZ(z, refs, seedj);
528 deltaz = zAtEnd[i] - zAtStart[j];
529 ddx = (zout[i].x-zin[j].x);
530 ddy = (zout[i].y-zin[j].y);
531 ddz = (zout[i].z-zin[j].z);
532 deltar = sqrt(ddx*ddx+ddy*ddy+ddz*ddz);
533 deltarxy = fabs(rInner[j]-rOuter[i]);
543 refs[0] = helixEnd[j]->getReferencePoint()[0];
544 refs[1] = helixEnd[j]->getReferencePoint()[1];
545 refs[2] = helixEnd[j]->getReferencePoint()[2];
546 helixEnd[j]->getPointInZ(z, refs, seedj);
547 deltaz = zAtEnd[i] - zAtEnd[j];
548 ddx = (zout[i].x-zout[j].x);
549 ddy = (zout[i].y-zout[j].y);
550 ddz = (zout[i].z-zout[j].z);
551 deltar = sqrt(ddx*ddx+ddy*ddy+ddz*ddz);
552 deltarxy = fabs(rInner[i]-rOuter[j]);
556 float dx = seedi[0]-seedj[0];
557 float dy = seedi[1]-seedj[1];
558 float dz = seedi[2]-seedj[2];
559 float dr = sqrt(dx*dx+dy*dy+dz*dz);
569 EVENT::MCParticleVec parents = mcParticle[j]->getParents();
570 if(parents.size()>0 && mcParticle[i]!=NULL){
571 for(
unsigned im = 0; im<parents.size();im++){
572 if(parents[im]==mcParticle[i] && momentum[i]>2.0){
575 if(abs(mcParticle[i]->getPDG())==321 &&
576 abs(mcParticle[j]->getPDG())==13)mcKink =
true;
577 if(abs(mcParticle[i]->getPDG())==321 &&
578 abs(mcParticle[j]->getPDG())==211)mcKink =
true;
579 if(abs(mcParticle[i]->getPDG())==3222 &&
580 abs(mcParticle[j]->getPDG())==211)mcKink =
true;
581 if(abs(mcParticle[i]->getPDG())==3212 &&
582 abs(mcParticle[j]->getPDG())==211)mcKink =
true;
583 if(abs(mcParticle[i]->getPDG())==3112 &&
584 abs(mcParticle[j]->getPDG())==211)mcKink =
true;
592 if(dr<100 || mcKink){
596 refsp[0] = helixEnd[ip]->getReferencePoint()[0];
597 refsp[1] = helixEnd[ip]->getReferencePoint()[1];
598 refsp[2] = helixEnd[ip]->getReferencePoint()[2];
599 refsd[0] = helixStart[id]->getReferencePoint()[0];
600 refsd[1] = helixStart[id]->getReferencePoint()[1];
601 refsd[2] = helixStart[id]->getReferencePoint()[2];
610 float zstep = (ze-zs)/10.;
613 for(
float zf = zs; zf < ze; zf+= zstep){
614 helixEnd[ip]->getPointInZ(zf, refsp, seedp);
615 helixStart[id]->getPointInZ(zf, refsd, seedd);
616 float dxf = seedp[0]-seedd[0];
617 float dyf = seedp[1]-seedd[1];
618 float dzf = seedp[2]-seedd[2];
619 float newdr = sqrt(dxf*dxf+dyf*dyf+dzf*dzf);
622 xkink = (seedp[0]+seedd[0])/2;
623 ykink = (seedp[1]+seedd[1])/2;
624 rkink = sqrt(xkink*xkink+ykink*ykink);
626 if(rkink<rOuter[i])rkink=rOuter[i];
627 if(rkink>rInner[j])rkink=rInner[j];
633 if(fabs(deltaz)>200)ok=
false;
634 if(fabs(deltaz)>100 && dr > 5.0)ok=
false;
636 float deltaRxyCut = -100;
652 if(rkink>
_rSIT[il])iSitLayer=il+1;
657 if(iSitLayer==_nLayersSIT){
661 if(iSitLayer>0 && iSitLayer <_nLayersSIT)deltaRxyCut =
_rSIT[iSitLayer] -
_rSIT[iSitLayer-1];
666 if(fabs(rOuter[i]-_rSIT[il])<10.)ili=il;
667 if(fabs(rInner[j]-_rSIT[il])<10.)ilo=il;
670 float fix = (_rSIT[ilo] - _rSIT[ili]);
672 if(fix>deltaRxyCut)deltaRxyCut = fix;
675 deltaRxyCut = deltaRxyCut*1.1;
682 if( (dr<drCut && deltarxy < deltaRxyCut*2) || mcKink){
683 bool possibleSplit =
false;
685 rkink = sqrt(xkink*xkink+ykink*ykink);
687 if( (rkink >
_rKinkCut && !flipped) || mcKink){
689 float massENu = this->
kinkMass(helixEnd[i],helixStart[j],0., 0.);
690 float massMuNu = this->
kinkMass(helixEnd[i],helixStart[j],
mMuon,0.);
695 float FmassENu = this->
kinkMass(helixEnd[i],helixEnd[j],0., 0.);
696 float FmassMuNu = this->
kinkMass(helixEnd[i],helixEnd[j],
mMuon,0.);
701 float tPion = fabs(zkink-zAtStart[i])*
mPion/fabs(momentumZ[i])/
cTauPion;
702 float tSigma = fabs(zkink-zAtStart[i])*
mSigma/fabs(momentumZ[i])/
cTauSigma;
703 float tKaon = fabs(zkink-zAtStart[i])*
mKaon/fabs(momentumZ[i])/
cTauKaon;
708 float probHyperon = 0;
711 if(deltaPion<1 && tPion > 0.001)probPion = 3.125*deltaPion*deltaPion+tPion;
716 float deltaKaon = deltaKaonMuNu;
717 if(deltaKaonPiPi<deltaKaon)deltaKaon = deltaKaonPiPi;
718 if(deltaKaon<1 && tKaon > 0.005)probKaon = 3.125*deltaKaon*deltaKaon+tKaon;
723 float deltaSigma = deltaSigmaPiN;
724 if(deltaSigmaPPi0<deltaSigma)deltaSigma = deltaSigmaPPi0;
725 if(deltaSigma<1 && tSigma <
_sigmaTimeCut)probSigma = 3.125*deltaSigma*deltaSigma+tSigma;
729 if(deltaHyperon<1 && tHyperon <
_hyperonTimeCut)probHyperon = 3.125*deltaHyperon*deltaHyperon+tHyperon;
731 bool goodKinkMass =
false;
732 if(probPion>0.0001||probKaon>0.0001||probSigma>0.0001||probHyperon>0.0001)goodKinkMass=
true;
735 float dpop = 2*fabs(momentum[i]-momentum[j])/(momentum[i]+momentum[j]);
736 float dp = fabs(momentum[i]-momentum[j]);
738 possibleSplit =
true;
741 if( (deltarxy<deltaRxyCut && dr<drCut) || possibleSplit ){
745 kinkij.
vtx[0] = xkink;
746 kinkij.
vtx[1] = ykink;
747 kinkij.
vtx[2] = zkink;
748 kinkij.
p[0] = helixStart[i]->getMomentum()[0];
749 kinkij.
p[1] = helixStart[i]->getMomentum()[1];
750 kinkij.
p[2] = helixStart[i]->getMomentum()[2];
755 if(deltarxy<2*deltaRxyCut && dr<drCut*2 ){
756 if(possibleSplit && charge[i]*charge[j]>0 ){
757 TrackerHitVec hitveci= tracks[i]->getTrackerHits();
758 TrackerHitVec hitvecj= tracks[j]->getTrackerHits();
759 int nhitsi = (int)hitveci.size();
760 int nhitsj = (int)hitvecj.size();
763 HelixClass* helixi = helixStart[j];
764 HelixClass* helixj = helixEnd[i];
773 float zmaxi = -99999;
774 float zmaxj = -99999;
775 for(
int ih =0;ih<nhitsi;++ih){
776 float x = (float)hitveci[ih]->getPosition()[0];
777 float y = (float)hitveci[ih]->getPosition()[1];
778 float zz = (float)hitveci[ih]->getPosition()[2];
779 if(fabs(zz)<zmini)zmini=fabs(zz);
780 if(fabs(zz)>zmaxi)zmaxi=fabs(zz);
787 helixj->getDistanceToPoint(hitxyz, dist);
788 if(dist[2]>maxdisti)maxdisti=dist[2];
789 if(dist[2]<25.)nclosei++;
791 for(
int ih =0;ih<nhitsj;++ih){
792 float x = (float)hitvecj[ih]->getPosition()[0];
793 float y = (float)hitvecj[ih]->getPosition()[1];
794 float zz = (float)hitvecj[ih]->getPosition()[2];
795 if(fabs(zz)<zminj)zminj=fabs(zz);
796 if(fabs(zz)>zmaxj)zmaxj=fabs(zz);
803 helixi->getDistanceToPoint(hitxyz, dist);
804 if(dist[2]>maxdistj)maxdistj=dist[2];
805 if(dist[2]<25.)nclosej++;
807 float fclosei = (float)nclosei/(
float)nhitsi;
808 float fclosej = (float)nclosej/(
float)nhitsj;
810 std::cout <<
" CAND SPLIT I : " << nhitsi <<
" ntpc " << ntpci <<
" nclose " << nclosei <<
" max " << maxdisti <<
" fclose : " << fclosei << std::endl;
811 std::cout <<
" CAND SPLIT J : " << nhitsj <<
" ntpc " << ntpcj <<
" nclose " << nclosej <<
" max " << maxdistj <<
" fclose : " << fclosej << std::endl;
813 if(maxdistj<50 && maxdisti < 50 && fclosej > 0.95 && fclosei > 0.95 && ntpcj+ntpci <
_tpcMaxRow+10.)split =
true;
814 splitDaughters[i].push_back(kinkij);
819 if(deltarxy<deltaRxyCut && dr<drCut ){
820 if(charge[i]*charge[j]>0 && goodKinkMass){
821 if(
_debugPrinting>0)std::cout <<
"Found kink candidate " << i <<
" " << j << std::endl;
822 if(probPion>0||probKaon>0||probSigma>0||probHyperon>0)goodKinkMass=
true;
823 if(probPion > probKaon &&
824 probPion > probSigma &&
825 probPion > probHyperon){
827 if(charge[i]<0)kinkij.
pdgCode = -211;
830 if(probKaon > probPion &&
831 probKaon > probSigma &&
832 probKaon > probHyperon){
835 if(charge[i]<0)kinkij.
pdgCode = -321;
837 if(probSigma > probPion &&
838 probSigma > probKaon &&
839 probSigma > probHyperon){
842 if(charge[i]<0)kinkij.
pdgCode = 3222;
844 if(probHyperon > probPion &&
845 probHyperon > probKaon &&
846 probHyperon > probSigma){
849 if(charge[i]>0)kinkij.
pdgCode = -3312;
851 kinkDaughters[i].push_back(kinkij);
856 if(deltarxy<deltaRxyCut && dr<drCut ){
858 if(
_debugPrinting>0)std::cout <<
"Found prong candidate " << i <<
" " << j << std::endl;
859 prongDaughters[i].push_back(kinkij);
861 if(charge[i]<0)kinkij.
pdgCode = -211;
868 if(mcParticle[j]!=NULL){
869 EVENT::MCParticleVec parents = mcParticle[j]->getParents();
870 if(parents.size()>0 && mcParticle[i]!=NULL){
871 for(
unsigned im = 0; im<parents.size();im++){
872 if(parents[im]==mcParticle[i])std::cout <<
" TRUE KINK . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . " << std::endl;
879 std::cout <<
" Candidate kink tracks : " << i <<
"," << j <<
" p[i] " << momentum[i] <<
" p[j] " << momentum[j] << std::endl;
880 if(flipped)std::cout <<
" Flipped Track " << std::endl;;
881 std::cout <<
" MC : ";
882 if(mcParticle[i]!=NULL)std::cout << mcParticle[i]->getPDG();
884 if(mcParticle[j]!=NULL)std::cout << mcParticle[j]->getPDG();
885 std::cout << std::endl;
886 std::cout <<
" Mass : " << massENu <<
" " << massMuNu <<
" " << massPiPi <<
" " << massPiN <<
" " << massPPi0 <<
" " << massPiL << std::endl;
887 if(flipped)std::cout <<
" MassF : " << FmassENu <<
" " << FmassMuNu <<
" " << FmassPiPi <<
" " << FmassPiN <<
" " << FmassPPi0 << FmassPiL << std::endl;
889 std::cout <<
" ProbPion : " << probPion <<
" TimePion : " << tPion <<
" Dm = " << massMuNu-
mPion << std::endl;
890 std::cout <<
" ProbKaon : " << probKaon <<
" TimeKaon : " << tKaon <<
891 " Dm = " << massMuNu-
mKaon <<
892 " Dm = " << massPiPi-
mKaon << std::endl;
893 std::cout <<
" ProbSigma : " << probSigma <<
" TimeSigma : " << tSigma <<
" Dm = " << massPiN-
mSigma <<
894 " Dm = " << massPPi0-
mSigma << std::endl;
895 std::cout <<
" ProbHyperon : " << probHyperon <<
" TimeHyperon : " << tHyperon <<
" Dm = " << massPiL-
mHyperon << std::endl;
896 std::cout <<
" Charge : " << i <<
"," << j <<
" q[i] " << charge[i] <<
" q[j] " << charge[j] << std::endl;
897 std::cout <<
" Rendi : " << i <<
"," << j <<
" rend " << rendi <<
" dr = " << dr <<
" (deltaR = " << deltar <<
")" << std::endl;
898 std::cout <<
" zkink : " << zkink <<
" rzykink " << rkink << std::endl;
899 if(deltarxy<deltaRxyCut)std::cout <<
" DeltaRxy vs cut : " << deltarxy <<
" < " << deltaRxyCut << std::endl;
900 if(deltarxy>deltaRxyCut)std::cout <<
" DeltaRxy vs cut : " << deltarxy <<
" > " << deltaRxyCut << std::endl;
901 if(dr<drCut)std::cout <<
" dr vs cut : " << dr <<
" < " << drCut << std::endl;
902 if(dr>drCut)std::cout <<
" dr vs cut : " << dr <<
" > " << drCut << std::endl;
903 std::cout <<
" zi/zj : " << zAtStart[i] <<
" - " << zAtEnd[i] <<
" " << zAtStart[j] <<
" - " << zAtEnd[j] << std::endl;
904 std::cout <<
" rinner/router : " << rInner[i] <<
" - " << rOuter[i] <<
" " << rInner[j] <<
" - " << rOuter[j] << std::endl;
916 for(
unsigned int i=0;i< tracks.size();++i){
919 if(kinkDaughters[i].size()>0 || prongDaughters[i].size()>0){
920 if(kinkDaughters[i].size()==1 && prongDaughters[i].size()<2){
934 for(
unsigned int i=0;i< tracks.size();++i){
935 if(kinkDaughters[i].size()>0 || prongDaughters[i].size()>0 || splitDaughters[i].size()>0){
937 if(kinkDaughters[i].size()>0){
938 std::cout <<
" Track " << i <<
" has " << kinkDaughters[i].size() <<
" kink daughters : ";
939 for(
unsigned j=0;j<kinkDaughters[i].size();j++)std::cout << kinkDaughters[i][j].trackj <<
" ";
940 std::cout << std::endl;
942 if(prongDaughters[i].size()>0){
943 std::cout <<
" Track " << i <<
" has " << prongDaughters[i].size() <<
" prong daughters : ";
944 for(
unsigned j=0;j<prongDaughters[i].size();j++)std::cout << prongDaughters[i][j].trackj <<
" ";
945 std::cout << std::endl;
947 if(splitDaughters[i].size()>0){
948 std::cout <<
" Track " << i <<
" has " << splitDaughters[i].size() <<
" split daughters : ";
949 for(
unsigned j=0;j<splitDaughters[i].size();j++)std::cout << splitDaughters[i][j].trackj <<
" ";
950 std::cout << std::endl;
955 if(splitDaughters[i].size()==1){
956 if(
_debugPrinting>0)std::cout <<
" Reconstructed SPLIT " << std::endl;
957 ReconstructedParticleImpl * part =
new ReconstructedParticleImpl();
958 VertexImpl * vtx =
new VertexImpl();
962 for (
int iC=0;iC<3;++iC) {
963 vertex[iC] = splitDaughters[i][0].vtx[iC];
964 mom[iC] = splitDaughters[i][0].p[iC];
966 float distance = splitDaughters[i][0].distance;
967 vtx->setPosition( vertex );
968 vtx->addParameter( distance );
969 part->setMomentum( mom );
970 part->setType( code );
973 std::cout <<
" Code = " << code <<
" Distance = " << distance << std::endl;
974 std::cout <<
" Vertex = ("
977 << vertex[2] <<
")" << std::endl;
978 std::cout <<
" Momentum = ("
981 << mom[2] <<
")" << std::endl;
983 float mass = splitDaughters[i][0].mass;
984 part->setMass( mass );
985 vtx->setAssociatedParticle( part );
986 part->setStartVertex( vtx );
987 part->addTrack( tracks[splitDaughters[i][0].tracki] );
988 part->addTrack( tracks[splitDaughters[i][0].trackj] );
989 if(colSplitRecoPart==NULL){
993 colSplitRecoPart->addElement( part );
994 colSplitVertex->addElement( vtx );
998 if(splitDaughters[i].size()!=1){
999 if(kinkDaughters[i].size()==1 && prongDaughters[i].size()<2){
1000 if(
_debugPrinting>0)std::cout <<
" Reconstructed KINKS " << std::endl;
1001 ReconstructedParticleImpl * part =
new ReconstructedParticleImpl();
1002 VertexImpl * vtx =
new VertexImpl();
1005 int code = kinkDaughters[i][0].pdgCode;
1006 for (
int iC=0;iC<3;++iC) {
1007 vertex[iC] = kinkDaughters[i][0].vtx[iC];
1008 mom[iC] = kinkDaughters[i][0].p[iC];
1010 float distance = kinkDaughters[i][0].distance;
1011 vtx->setPosition( vertex );
1012 vtx->addParameter( distance );
1013 part->setMomentum( mom );
1014 part->setType( code );
1016 std::cout <<
" Code = " << code <<
" Distance = " << distance << std::endl;
1017 std::cout <<
" Vertex = ("
1020 << vertex[2] <<
")" << std::endl;
1021 std::cout <<
" Momentum = ("
1024 << mom[2] <<
")" << std::endl;
1026 float mass = kinkDaughters[i][0].mass;
1027 part->setMass( mass );
1028 vtx->setAssociatedParticle( part );
1029 part->setStartVertex( vtx );
1030 part->addTrack( tracks[kinkDaughters[i][0].tracki] );
1031 part->addTrack( tracks[kinkDaughters[i][0].trackj] );
1032 if(colKinkRecoPart==NULL){
1036 colKinkRecoPart->addElement( part );
1037 colKinkVertex->addElement( vtx );
1040 }
else if(prongDaughters[i].size() > 0 ) {
1042 if(
_debugPrinting>0)std::cout <<
" Reconstructed PRONG " << std::endl;
1043 ReconstructedParticleImpl * part =
new ReconstructedParticleImpl();
1044 VertexImpl * vtx =
new VertexImpl();
1048 for (
int iC=0;iC<3;++iC) {
1049 vertex[iC] = prongDaughters[i][0].vtx[iC];
1050 mom[iC] = prongDaughters[i][0].p[iC];
1052 float distance = prongDaughters[i][0].distance;
1053 vtx->setPosition( vertex );
1054 vtx->addParameter( distance );
1055 part->setMomentum( mom );
1056 part->setType( code );
1058 std::cout <<
" Code = " << code <<
" Distance = " << distance << std::endl;
1059 std::cout <<
" Vertex = ("
1062 << vertex[2] <<
")" << std::endl;
1063 std::cout <<
" Momentum = ("
1066 << mom[2] <<
")" << std::endl;
1068 float mass = prongDaughters[i][0].mass;
1069 part->setMass( mass );
1070 vtx->setAssociatedParticle( part );
1071 part->setStartVertex( vtx );
1072 part->addTrack( tracks[prongDaughters[i][0].tracki] );
1073 for(
unsigned id=0;
id<prongDaughters[i].size();
id++)part->addTrack( tracks[prongDaughters[i][
id].trackj] );
1074 if(colProngRecoPart==NULL){
1078 colProngRecoPart->addElement( part );
1079 colProngVertex->addElement( vtx );
1089 if(colKinkRecoPart!=NULL){
1093 if(colProngRecoPart!=NULL){
1097 if(colSplitRecoPart!=NULL){
1102 for(
unsigned int itrack=0;itrack< tracks.size();++itrack){
1103 delete helixEnd[itrack];
1104 delete helixStart[itrack];
1109 if(trackNavigator != NULL)
delete trackNavigator;
1119 int sizeOfVector = int(trkPairVec.size());
1120 TrackPair *one,*two,*Temp;
1122 for (
int i = 0 ; i < sizeOfVector-1; i++)
1123 for (
int j = 0; j < sizeOfVector-i-1; j++)
1125 one = trkPairVec[j];
1126 two = trkPairVec[j+1];
1127 if( one->getDistance() > two->getDistance() )
1129 Temp = trkPairVec[j];
1130 trkPairVec[j] = trkPairVec[j+1];
1131 trkPairVec[j+1] = Temp;
1142 parentMom[0] = parent->getMomentum()[0];
1143 parentMom[1] = parent->getMomentum()[1];
1144 parentMom[2] = parent->getMomentum()[2];
1145 float daughterMom[4];
1146 daughterMom[0] = daughter->getMomentum()[0];
1147 daughterMom[1] = daughter->getMomentum()[1];
1148 daughterMom[2] = daughter->getMomentum()[2];
1149 float daughterE = sqrt(daughterMom[0]*daughterMom[0] + daughterMom[1]*daughterMom[1]+
1150 daughterMom[2]*daughterMom[2] + daughterMass*daughterMass);
1153 pnu[0] = parentMom[0]-daughterMom[0];
1154 pnu[1] = parentMom[1]-daughterMom[1];
1155 pnu[2] = parentMom[2]-daughterMom[2];
1157 float Enu = sqrt(pnu[0]*pnu[0]+pnu[1]*pnu[1]+pnu[2]*pnu[2]+neutralMass*neutralMass);
1158 float mx = sqrt((daughterE+Enu)*(daughterE+Enu)-parentMom[0]*parentMom[0]-
1159 parentMom[1]*parentMom[1]-parentMom[2]*parentMom[2]);
std::vector< float > _rVTX
KinkFinder Processor KinkFinder processor identify kinked tracks
std::string _kinkVertexColName
std::string _prongRecoPartColName
void Sorting(TrackPairVec &trkPairVec)
std::string _splitRecoPartColName
virtual void check(LCEvent *evt)
std::string _prongVertexColName
float _maxSplitTrackDeltaP
std::string _splitVertexColName
float _maxSplitTrackFracDeltaP
std::vector< float > _rSIT
std::vector< LCCollection * > LCCollectionVec
float _hyperonDecayMassCut
std::string _kinkRecoPartColName
virtual void processRunHeader(LCRunHeader *run)
std::string _trackColName
virtual void processEvent(LCEvent *evt)
float kinkMass(HelixClass *parent, HelixClass *daughter, float daughterMass, float neutralMass)