CMS 3D CMS Logo

/data/refman/pasoursint/CMSSW_4_4_5_patch3/src/RecoTracker/SingleTrackPattern/src/CRackTrajectoryBuilder.cc

Go to the documentation of this file.
00001 //
00002 // Package:         RecoTracker/SingleTrackPattern
00003 // Class:           CRackTrajectoryBuilder
00004 // Original Author:  Michele Pioppi-INFN perugia
00005 //
00006 // Package:         RecoTracker/SingleTrackPattern
00007 // Class:           CRackTrajectoryBuilder
00008 // Original Author:  Michele Pioppi-INFN perugia
00009 
00010 #include <vector>
00011 #include <iostream>
00012 #include <cmath>
00013 
00014 #include "RecoTracker/SingleTrackPattern/interface/CRackTrajectoryBuilder.h"
00015 #include "DataFormats/Common/interface/OwnVector.h"
00016 #include "TrackingTools/TransientTrackingRecHit/interface/TransientTrackingRecHit.h"
00017 #include "TrackingTools/TrajectoryState/interface/BasicSingleTrajectoryState.h"
00018 #include "MagneticField/Records/interface/IdealMagneticFieldRecord.h"
00019 #include "FWCore/ParameterSet/interface/ParameterSet.h"
00020 #include "DataFormats/GeometryVector/interface/GlobalPoint.h"
00021 #include "FWCore/MessageLogger/interface/MessageLogger.h"
00022 #include "TrackingTools/Records/interface/TrackingComponentsRecord.h" 
00023 #include "TrackingTools/Records/interface/TransientRecHitRecord.h" 
00024 #include "TrackingTools/TrackFitters/interface/TrajectoryStateWithArbitraryError.h"
00025 
00026 
00027 //#include "RecoTracker/CkfPattern/interface/TransientInitialStateEstimator.h"
00028 
00029 using namespace std;
00030 
00031 
00032 CRackTrajectoryBuilder::CRackTrajectoryBuilder(const edm::ParameterSet& conf) : conf_(conf) { 
00033   //minimum number of hits per tracks
00034 
00035   theMinHits=conf_.getParameter<int>("MinHits");
00036   //cut on chi2
00037   chi2cut=conf_.getParameter<double>("Chi2Cut");
00038   edm::LogInfo("CosmicTrackFinder")<<"Minimum number of hits "<<theMinHits<<" Cut on Chi2= "<<chi2cut;
00039 
00040   debug_info=conf_.getUntrackedParameter<bool>("debug", false);
00041   fastPropagation=conf_.getUntrackedParameter<bool>("fastPropagation", false);
00042   useMatchedHits=conf_.getUntrackedParameter<bool>("useMatchedHits", true);
00043 
00044 
00045   geometry=conf_.getUntrackedParameter<std::string>("GeometricStructure","STANDARD");
00046 
00047   
00048 
00049 }
00050 
00051 
00052 CRackTrajectoryBuilder::~CRackTrajectoryBuilder() {
00053 //  delete theInitialState;
00054 }
00055 
00056 
00057 void CRackTrajectoryBuilder::init(const edm::EventSetup& es, bool seedplus){
00058 
00059 
00060 //  edm::ParameterSet tise_params = conf_.getParameter<edm::ParameterSet>("TransientInitialStateEstimatorParameters") ;
00061 // theInitialState          = new TransientInitialStateEstimator( es,tise_params);
00062 
00063   //services
00064   es.get<IdealMagneticFieldRecord>().get(magfield);
00065   es.get<TrackerDigiGeometryRecord>().get(tracker);
00066   
00067  
00068   
00069   if (seedplus) {        
00070     seed_plus=true;      
00071     thePropagator=      new PropagatorWithMaterial(alongMomentum,0.1057,&(*magfield) );          
00072     thePropagatorOp=    new PropagatorWithMaterial(oppositeToMomentum,0.1057,&(*magfield) );}    
00073   else {
00074     seed_plus=false;
00075     thePropagator=      new PropagatorWithMaterial(oppositeToMomentum,0.1057,&(*magfield) );    
00076     thePropagatorOp=    new PropagatorWithMaterial(alongMomentum,0.1057,&(*magfield) );
00077   }
00078   
00079   theUpdator=       new KFUpdator();
00080 //  theUpdator=       new KFStripUpdator();
00081   theEstimator=     new Chi2MeasurementEstimator(chi2cut);
00082   
00083 
00084   edm::ESHandle<TransientTrackingRecHitBuilder> theBuilder;
00085   std::string builderName = conf_.getParameter<std::string>("TTRHBuilder");   
00086   es.get<TransientRecHitRecord>().get(builderName,theBuilder);
00087   
00088 
00089   RHBuilder=   theBuilder.product();
00090 
00091 
00092 
00093 
00094   theFitter=        new KFTrajectoryFitter(*thePropagator,
00095                                            *theUpdator, 
00096                                            *theEstimator) ;
00097   
00098 
00099   theSmoother=      new KFTrajectorySmoother(*thePropagatorOp,
00100                                              *theUpdator,       
00101                                              *theEstimator);
00102   
00103 }
00104 
00105 
00106 void CRackTrajectoryBuilder::run(const TrajectorySeedCollection &collseed,
00107                                   const SiStripRecHit2DCollection &collstereo,
00108                                   const SiStripRecHit2DCollection &collrphi ,
00109                                   const SiStripMatchedRecHit2DCollection &collmatched,
00110                                   const SiPixelRecHitCollection &collpixel,
00111                                   const edm::EventSetup& es,
00112                                   edm::Event& e,
00113                                   vector<Trajectory> &trajoutput)
00114 {
00115 
00116   std::vector<Trajectory> trajSmooth;
00117   std::vector<Trajectory>::iterator trajIter;
00118   
00119   TrajectorySeedCollection::const_iterator iseed;
00120   unsigned int IS=0;
00121   for(iseed=collseed.begin();iseed!=collseed.end();iseed++){
00122     bool seedplus=((*iseed).direction()==alongMomentum);
00123     init(es,seedplus);
00124     hits.clear();
00125     trajFit.clear();
00126     trajSmooth.clear();
00127 
00128     Trajectory startingTraj = createStartingTrajectory(*iseed);
00129     Trajectory trajTmp; // used for the opposite direction
00130     Trajectory traj = startingTraj;
00131 
00132    
00133     //first propagate track in opposite direction ...
00134     seed_plus = !seed_plus;
00135     vector<const TrackingRecHit*> allHitsOppsite = SortHits(collstereo,collrphi,collmatched,collpixel, *iseed, true);
00136     seed_plus = !seed_plus;
00137     if (allHitsOppsite.size())
00138       {
00139         //there are hits which are above the seed,
00140         //cout << "Number of hits higher than seed " <<allHitsOppsite.size() << endl;   
00141         
00142         AddHit( traj, allHitsOppsite, thePropagatorOp);
00143         
00144         
00145         if (debug_info)
00146           {
00147             cout << "Hits in opposite direction..." << endl;
00148             TransientTrackingRecHit::RecHitContainer::const_iterator iHit;
00149             for ( iHit = hits.begin(); iHit!=hits.end(); iHit++)
00150               {
00151                 cout <<  (**iHit).globalPosition() << endl;
00152               }
00153           }
00154         
00155         
00156         // now add hist opposite to seed
00157         //now crate new starting trajectory
00158         reverse(hits.begin(), hits.end());
00159         if (thePropagatorOp->propagate(traj.firstMeasurement().updatedState(),
00160                                        tracker->idToDet((hits.front())->geographicalId())->surface()).isValid()){
00161           TSOS startingStateNew =  //TrajectoryStateWithArbitraryError()//
00162             (thePropagatorOp->propagate(traj.firstMeasurement().updatedState(),
00163                                         tracker->idToDet((hits.front())->geographicalId())->surface()));
00164           
00165           if (debug_info)
00166             {
00167               cout << "Hits in opposite direction reversed..." << endl;
00168               TransientTrackingRecHit::RecHitContainer::const_iterator iHit;
00169               for ( iHit = hits.begin(); iHit!=hits.end(); iHit++)
00170                 {
00171                   cout <<  (**iHit).globalPosition() << endl;
00172                 }
00173             }
00174           
00175           const TrajectorySeed& tmpseed=traj.seed();
00176           trajTmp = theFitter->fit(tmpseed,hits, startingStateNew ).front();
00177           
00178           if(debug_info){
00179             cout << "Debugging show fitted hits" << endl;           
00180                 std::vector< ConstReferenceCountingPointer< TransientTrackingRecHit> > hitsFit= trajTmp.recHits();
00181                 std::vector< ConstReferenceCountingPointer< TransientTrackingRecHit> >::const_iterator hit;
00182                 for(hit=hitsFit.begin();hit!=hitsFit.end();hit++){
00183                   
00184                   cout << RHBuilder->build( &(*(*hit)->hit()) )->globalPosition() << endl;
00185                 }
00186           }
00187           
00188         }
00189       }
00190     else 
00191       {
00192         if(debug_info) cout << "There are no hits in opposite direction ..." << endl;
00193       }
00194 
00195     vector<const TrackingRecHit*> allHits;
00196     if (trajTmp.foundHits())
00197       {
00198         traj = trajTmp;
00199         allHits= SortHits(collstereo,collrphi,collmatched,collpixel,*iseed, false);       
00200       }
00201     else
00202       {
00203         traj = startingTraj;
00204         hits.clear();
00205         allHits= SortHits(collstereo,collrphi,collmatched,collpixel,*iseed, true);        
00206       }
00207     
00208     AddHit( traj,allHits, thePropagator);
00209     
00210     
00211     if(debug_info){
00212       cout << "Debugging show All fitted hits" << endl;     
00213       std::vector< ConstReferenceCountingPointer< TransientTrackingRecHit> > hits= traj.recHits();
00214             std::vector< ConstReferenceCountingPointer< TransientTrackingRecHit> >::const_iterator hit;
00215             for(hit=hits.begin();hit!=hits.end();hit++){
00216               
00217               cout << RHBuilder->build( &(*(*hit)->hit()) )->globalPosition() << endl;
00218             }
00219 
00220             cout << qualityFilter( traj) << " <- quality filter good?" << endl;
00221           }
00222 
00223 
00224     if (debug_info) cout << "now do quality checks" << endl;
00225     if ( qualityFilter( traj) ) {
00226       const TrajectorySeed& tmpseed=traj.seed();
00227       std::pair<TrajectoryStateOnSurface, const GeomDet*> initState =  innerState(traj); //theInitialState->innerState(traj);
00228         if (initState.first.isValid())
00229               trajFit = theFitter->fit(tmpseed,hits, initState.first);
00230     }
00231 
00232     for (trajIter=trajFit.begin(); trajIter!=trajFit.end();trajIter++){
00233       trajSmooth=theSmoother->trajectories((*trajIter));
00234     }
00235     for (trajIter= trajSmooth.begin(); trajIter!=trajSmooth.end();trajIter++){
00236       if((*trajIter).isValid()){
00237 
00238         if (debug_info) cout << "adding track ... " << endl;
00239         trajoutput.push_back((*trajIter));
00240       }
00241     }
00242     delete theUpdator;
00243     delete theEstimator;
00244     delete thePropagator;
00245     delete thePropagatorOp;
00246     delete theFitter;
00247     delete theSmoother;
00248     //Only the first 30 seeds are considered
00249     if (IS>30) return;
00250     IS++;
00251 
00252   }
00253 }
00254 
00255 Trajectory CRackTrajectoryBuilder::createStartingTrajectory( const TrajectorySeed& seed) const
00256 {
00257   Trajectory result( seed, seed.direction());
00258   std::vector<TM> seedMeas = seedMeasurements(seed);
00259   if ( !seedMeas.empty()) {
00260     for (std::vector<TM>::const_iterator i=seedMeas.begin(); i!=seedMeas.end(); i++){
00261       result.push(*i);
00262     }
00263   }
00264  
00265   return result;
00266 }
00267 
00268 
00269 std::vector<TrajectoryMeasurement> 
00270 CRackTrajectoryBuilder::seedMeasurements(const TrajectorySeed& seed) const
00271 {
00272   std::vector<TrajectoryMeasurement> result;
00273   TrajectorySeed::range hitRange = seed.recHits();
00274   for (TrajectorySeed::const_iterator ihit = hitRange.first; 
00275        ihit != hitRange.second; ihit++) {
00276     //RC TransientTrackingRecHit* recHit = RHBuilder->build(&(*ihit));
00277     TransientTrackingRecHit::RecHitPointer recHit = RHBuilder->build(&(*ihit));
00278     const GeomDet* hitGeomDet = (&(*tracker))->idToDet( ihit->geographicalId());
00279     TSOS invalidState( new BasicSingleTrajectoryState( hitGeomDet->surface()));
00280 
00281     if (ihit == hitRange.second - 1) {
00282       TSOS  updatedState=startingTSOS(seed);
00283       result.push_back(TM( invalidState, updatedState, recHit));
00284 
00285     } 
00286     else {
00287       result.push_back(TM( invalidState, recHit));
00288     }
00289     
00290   }
00291 
00292   return result;
00293 }
00294 
00295 vector<const TrackingRecHit*> 
00296 CRackTrajectoryBuilder::SortHits(const SiStripRecHit2DCollection &collstereo,
00297                                   const SiStripRecHit2DCollection &collrphi ,
00298                                   const SiStripMatchedRecHit2DCollection &collmatched,
00299                                   const SiPixelRecHitCollection &collpixel,
00300                                   const TrajectorySeed &seed,
00301                                   const bool bAddSeedHits
00302                                   ){
00303 
00304 
00305   //The Hits with global y more than the seed are discarded
00306   //The Hits correspondign to the seed are discarded
00307   //At the end all the hits are sorted in y
00308   vector<const TrackingRecHit*> allHits;
00309 
00310   SiStripRecHit2DCollection::DataContainer::const_iterator istrip;
00311   TrajectorySeed::range hRange= seed.recHits();
00312   TrajectorySeed::const_iterator ihit;
00313   float yref=0.;
00314 
00315   if (debug_info) cout << "SEED " << startingTSOS(seed) << endl; 
00316   if (debug_info) cout << "seed hits size " << seed.nHits() << endl;
00317 
00318 
00319   //seed debugging:
00320  // GeomDet *seedDet =  tracker->idToDet(seed.startingState().detId());
00321 
00322 
00323 //  edm::LogInfo("CRackTrajectoryBuilder::SortHits") << "SEED " << seed.startingState(); 
00324 
00325   edm::LogInfo("CRackTrajectoryBuilder::SortHits") << "SEED " << startingTSOS(seed); 
00326 //  edm::LogInfo("CRackTrajectoryBuilder::SortHits" << "seed hits size " << seed.nHits();
00327 
00328 
00329 
00330   //  if (seed.nHits()<2)
00331   //  return allHits;
00332 
00333   float_t yMin=0.;
00334   float_t yMax=0.;
00335 
00336   int seedHitSize= hRange.second - hRange.first;
00337 
00338   vector <int> detIDSeedMatched (seedHitSize);
00339   vector <int> detIDSeedRphi (seedHitSize);
00340   vector <int> detIDSeedStereo (seedHitSize);
00341 
00342   for (ihit = hRange.first; 
00343        ihit != hRange.second; ihit++) {
00344 
00345      // need to find track with lowest (seed_plus)/ highest y (seed_minus)
00346     // split matched hits ...
00347    const SiStripMatchedRecHit2D* matchedhit=dynamic_cast<const SiStripMatchedRecHit2D*>(&(*ihit));
00348 
00349    yref=RHBuilder->build(&(*ihit))->globalPosition().y();
00350    if (ihit == hRange.first)
00351      {
00352         yMin = yref;
00353         yMax = yref; 
00354      }
00355 
00356    if (matchedhit)
00357      {
00358        float_t yGlobRPhi   = RHBuilder->build( (matchedhit->monoHit()))->globalPosition().y();
00359        float_t yGlobStereo = RHBuilder->build( (matchedhit->stereoHit()))->globalPosition().y();
00360 
00361        if (debug_info) cout << "Rphi ..." << yGlobRPhi << endl;
00362        if (debug_info) cout << "Stereo ..." << yGlobStereo << endl;
00363 
00364        if ( yGlobStereo < yMin ) yMin = yGlobStereo;
00365        if ( yGlobRPhi   < yMin ) yMin = yGlobRPhi;
00366 
00367        if ( yGlobStereo > yMax ) yMax = yGlobStereo;
00368        if ( yGlobRPhi   > yMax ) yMax = yGlobRPhi;
00369 
00370        detIDSeedMatched.push_back (  matchedhit->geographicalId().rawId() );
00371        detIDSeedRphi.push_back ( matchedhit->monoHit()->geographicalId().rawId() );
00372        detIDSeedStereo.push_back ( matchedhit->stereoHit()->geographicalId().rawId() );
00373 
00374       if (bAddSeedHits)
00375         {
00376           if (useMatchedHits) 
00377             {
00378               
00379               hits.push_back((RHBuilder->build(&(*ihit)))); 
00380             }
00381           else
00382             {
00383               if ( ( (yGlobRPhi > yGlobStereo ) && seed_plus ) || ((yGlobRPhi < yGlobStereo ) && !seed_plus ))  
00384                 {
00385                   hits.push_back((RHBuilder->build(matchedhit->monoHit())));
00386                   hits.push_back((RHBuilder->build(matchedhit->stereoHit())));
00387                 }
00388               else
00389                 {
00390                   hits.push_back((RHBuilder->build(matchedhit->stereoHit())));     
00391                   hits.push_back((RHBuilder->build(matchedhit->monoHit())));
00392                   
00393                 }
00394             }
00395         }
00396      }
00397    else if (bAddSeedHits)
00398      {
00399        hits.push_back((RHBuilder->build(&(*ihit)))); 
00400        detIDSeedRphi.push_back ( ihit->geographicalId().rawId() );
00401        detIDSeedMatched.push_back ( -1 );
00402        detIDSeedStereo.push_back ( -1 );
00403        
00404      }
00405        
00406    if ( yref < yMin ) yMin = yref;
00407    if ( yref > yMax ) yMax = yref;
00408    
00409 //    if (bAddSeedHits)
00410 //      hits.push_back((RHBuilder->build(&(*ihit)))); 
00411 
00412     LogDebug("CosmicTrackFinder")<<"SEED HITS"<<RHBuilder->build(&(*ihit))->globalPosition();
00413     if (debug_info) cout <<"SEED HITS"<<RHBuilder->build(&(*ihit))->globalPosition() << endl;
00414 //    if (debug_info) cout <<"SEED HITS"<< seed.startingState().parameters() << endl;
00415 
00416 
00417   }
00418   
00419   yref = (seed_plus) ? yMin : yMax;
00420   
00421   if ((&collpixel)!=0){
00422     SiPixelRecHitCollection::DataContainer::const_iterator ipix;
00423     for(ipix=collpixel.data().begin();ipix!=collpixel.data().end();ipix++){
00424       float ych= RHBuilder->build(&(*ipix))->globalPosition().y();
00425       if ((seed_plus && (ych<yref)) || (!(seed_plus) && (ych>yref)))
00426         allHits.push_back(&(*ipix));
00427     }
00428   } 
00429   
00430 
00431   if (useMatchedHits) // use matched
00432     {
00433         //add the matched hits ...
00434       SiStripMatchedRecHit2DCollection::DataContainer::const_iterator istripm;
00435 
00436       if ((&collmatched)!=0){
00437         for(istripm=collmatched.data().begin();istripm!=collmatched.data().end();istripm++){
00438           float ych= RHBuilder->build(&(*istripm))->globalPosition().y();
00439 
00440           int cDetId=istripm->geographicalId().rawId();
00441           bool noSeedDet = ( detIDSeedMatched.end() == find (detIDSeedMatched.begin(), detIDSeedMatched.end(), cDetId ) ) ;
00442 
00443           if ( noSeedDet )
00444           if ((seed_plus && (ych<yref)) || (!(seed_plus) && (ych>yref)))
00445             {
00446           //if (debug_info) cout << "adding matched hit " << &(*istripm) << endl; 
00447               allHits.push_back(&(*istripm));
00448         }
00449         }
00450       }
00451 
00452    //add the rpi hits, but only accept hits that are not matched hits
00453   if ((&collrphi)!=0){
00454     for(istrip=collrphi.data().begin();istrip!=collrphi.data().end();istrip++){
00455       float ych= RHBuilder->build(&(*istrip))->globalPosition().y();
00456       StripSubdetector monoDetId(istrip->geographicalId());
00457       if (monoDetId.partnerDetId())
00458         {
00459           edm::LogInfo("CRackTrajectoryBuilder::SortHits")  << "this det belongs to a glued det " << ych << endl;
00460           continue;
00461         }
00462           int cDetId=istrip->geographicalId().rawId();
00463           bool noSeedDet = ( detIDSeedRphi.end()== find (detIDSeedRphi.begin(), detIDSeedRphi.end(), cDetId ) ) ;
00464           if (noSeedDet)
00465       if ((seed_plus && (ych<yref)) || (!(seed_plus) && (ych>yref)))
00466         {
00467          
00468           bool hitIsUnique = true;
00469           //now 
00470            if ((&collmatched)!=0)
00471              for(istripm=collmatched.data().begin();istripm!=collmatched.data().end();istripm++)
00472                {
00473                  //              if ( isDifferentStripReHit2D ( *istrip, * (istripm->stereoHit() ) ) == false)
00474                    if ( isDifferentStripReHit2D ( *istrip, * (istripm->monoHit() ) ) == false)
00475                    {
00476                      hitIsUnique = false;
00477                      edm::LogInfo("CRackTrajectoryBuilder::SortHits")  << "rphi hit is in matched hits; y: " << ych << endl;
00478                      break;
00479                    }
00480                } //end loop over all matched
00481            if (hitIsUnique)
00482              {
00483                  //      if (debug_info) cout << "adding rphi hit " << &(*istrip) << endl; 
00484                 allHits.push_back(&(*istrip));   
00485              }
00486         }
00487     }
00488   }
00489 
00490   
00491   //add the stereo hits except the hits that are in the matched collection
00492   //update do not use unmatched rphi hist due to limitation of alignment framework
00493   //if (!useMatchedHits)
00494   //if ((&collstereo)!=0){
00495   //  for(istrip=collstereo.data().begin();istrip!=collstereo.data().end();istrip++){
00496   //    float ych= RHBuilder->build(&(*istrip))->globalPosition().y();
00497   //
00498   //
00499   //      int cDetId = istrip->geographicalId().rawId();
00500   //        bool noSeedDet = ( detIDSeedStereo.end()== find (detIDSeedStereo.begin(), detIDSeedStereo.end(), cDetId ) ) ;
00501   //
00502   //        if (noSeedDet)
00503   //    if ((seed_plus && (ych<yref)) || (!(seed_plus) && (ych>yref)))
00504   //      {
00505   //
00506   //        bool hitIsUnique = true;
00507   //        //now 
00508   //         if ((&collmatched)!=0)
00509   //           for(istripm=collmatched.data().begin();istripm!=collmatched.data().end();istripm++)
00510   //             {
00511   //             if ( isDifferentStripReHit2D ( *istrip, * (istripm->stereoHit() ) ) == false)
00512   //               {
00513   //                 hitIsUnique = false;
00514   //                 edm::LogInfo("CRackTrajectoryBuilder::SortHits") << "stereo hit already in matched hits; y:  " << ych << endl;
00515   //                 break;
00516   //               }
00517   //             } //end loop over all stereo
00518   //         if (hitIsUnique)
00519   //           {
00520   //             
00521   //          //   if (debug_info) cout << "now I am adding a stero hit, either noise or not in overlap ...!!!!" << endl;
00522   //                allHits.push_back(&(*istrip));   
00523   //           }
00524   //      }
00525   //  }
00526   //}
00527     }
00528   else // dont use matched ...
00529     {
00530       
00531       if ((&collrphi)!=0){
00532         for(istrip=collrphi.data().begin();istrip!=collrphi.data().end();istrip++){
00533           float ych= RHBuilder->build(&(*istrip))->globalPosition().y();
00534           if ((seed_plus && (ych<yref)) || (!(seed_plus) && (ych>yref)))
00535             allHits.push_back(&(*istrip));   
00536         }
00537       }
00538 
00539 
00540       if ((&collstereo)!=0){
00541         for(istrip=collstereo.data().begin();istrip!=collstereo.data().end();istrip++){
00542           float ych= RHBuilder->build(&(*istrip))->globalPosition().y();
00543           if ((seed_plus && (ych<yref)) || (!(seed_plus) && (ych>yref)))
00544             allHits.push_back(&(*istrip));
00545         }
00546       }
00547 
00548     }
00549 
00550 
00551 //  if (seed_plus){
00552 //    stable_sort(allHits.begin(),allHits.end(),CompareDetY_plus(*tracker));
00553 //  }
00554 //  else {
00555 //    stable_sort(allHits.begin(),allHits.end(),CompareDetY_minus(*tracker));
00556 //  }
00557 
00558 
00559   if (seed_plus){
00560       stable_sort(allHits.begin(),allHits.end(),CompareHitY_plus(*tracker));
00561   }
00562   else {
00563       stable_sort(allHits.begin(),allHits.end(),CompareHitY(*tracker));
00564   }
00565 
00566 
00567 
00568   if (debug_info) 
00569     {
00570       if (debug_info) cout << "all hits" << endl;
00571 
00572       //starting trajectory
00573       Trajectory startingTraj = createStartingTrajectory(seed);
00574 
00575       if (debug_info) cout << "START " << startingTraj.lastMeasurement().updatedState() << endl;
00576       if (debug_info) cout << "START  Err" << startingTraj.lastMeasurement().updatedState().localError().matrix() << endl;
00577 
00578 
00579       vector<const TrackingRecHit*>::iterator iHit;
00580       for (iHit=allHits.begin(); iHit<allHits.end(); iHit++)
00581         {
00582               GlobalPoint gphit=RHBuilder->build(*iHit)->globalPosition();
00583               if (debug_info) cout << "GH " << gphit << endl;
00584 
00585               //      tracker->idToDet((*iHit)->geographicalId())->surface();
00586 
00587       TSOS prSt = thePropagator->propagate(startingTraj.lastMeasurement().updatedState(),
00588                           tracker->idToDet((*iHit)->geographicalId())->surface());
00589               
00590               if(prSt.isValid()) 
00591                 {
00592       if (debug_info) cout << "PR " << prSt.globalPosition() << endl;
00593       //if (debug_info) cout << "PR  Err" << prSt.localError().matrix() << endl;
00594                   
00595                 }
00596               else
00597                 {
00598                   if (debug_info) cout << "not valid" << endl;
00599                 }
00600         }
00601               if (debug_info) cout << "all hits end" << endl;
00602     }
00603 
00604 
00605   return allHits;
00606 }
00607 
00608 TrajectoryStateOnSurface
00609 CRackTrajectoryBuilder::startingTSOS(const TrajectorySeed& seed)const
00610 {
00611   PTrajectoryStateOnDet pState( seed.startingState());
00612   const GeomDet* gdet  = (&(*tracker))->idToDet(DetId(pState.detId()));
00613   TSOS  State= tsTransform.transientState( pState, &(gdet->surface()), 
00614                                            &(*magfield));
00615   return State;
00616 
00617 }
00618 
00619 void CRackTrajectoryBuilder::AddHit(Trajectory &traj,
00620                                      vector<const TrackingRecHit*>Hits, Propagator *currPropagator){
00621 
00622    if ( Hits.size() == 0 )
00623      return;
00624   
00625    if (debug_info) cout << "CRackTrajectoryBuilder::AddHit" << endl;
00626    if (debug_info) cout << "START " << traj.lastMeasurement().updatedState() << endl;
00627  
00628    vector <TrackingRecHitRange> hitRangeByDet;
00629    TrackingRecHitIterator prevDet;
00630  
00631    prevDet = Hits.begin();
00632    for( TrackingRecHitIterator iHit = Hits.begin(); iHit != Hits.end(); iHit++ )
00633      {
00634        if ( (*prevDet)->geographicalId() == (*iHit)->geographicalId() ) 
00635         continue;
00636         
00637        hitRangeByDet.push_back( make_pair( prevDet, iHit ) );
00638        prevDet = iHit;
00639       }
00640    hitRangeByDet.push_back( make_pair( prevDet, Hits.end() ) );
00641  
00643  
00644      if (fastPropagation) {
00645        for( TrackingRecHitRangeIterator iHitRange = hitRangeByDet.begin(); iHitRange != hitRangeByDet.end(); iHitRange++ )
00646          {
00647             const TrackingRecHit *currHit = *(iHitRange->first);
00648           DetId      currDet = currHit->geographicalId();
00649   
00650            TSOS prSt= currPropagator->propagate(traj.lastMeasurement().updatedState(),
00651                                               tracker->idToDet(currDet)->surface());
00652   
00653            if ( !prSt.isValid())
00654             {
00655               if (debug_info) cout << "Not Valid: PRST" << prSt.globalPosition();
00656  //           if (debug_info) cout << "Not Valid: HIT" << *currHit;
00657  
00658  
00659               continue;
00660             }
00661  
00662            TransientTrackingRecHit::RecHitPointer bestHit = RHBuilder->build( currHit );
00663            double chi2min = theEstimator->estimate( prSt, *bestHit).second;
00664  
00665            if (debug_info) cout << "Size " << iHitRange->first - (*iHitRange).second << endl;
00666            for( TrackingRecHitIterator iHit = (*iHitRange).first+1; iHit != iHitRange->second; iHit++ )
00667              {
00668                if (debug_info) cout << "loop3 " <<" "<< Hits.end() - iHit << endl;
00669  
00670                TransientTrackingRecHit::RecHitPointer tmpHit = RHBuilder->build( *iHit );
00671                double currChi2 = theEstimator->estimate(prSt, *tmpHit).second;
00672                if ( currChi2 < chi2min )
00673                  {
00674                    currChi2 = chi2min;
00675                    bestHit = tmpHit;
00676                  }
00677              }
00678            //now we have check if the track can be added to the trajectory
00679            if (debug_info) cout << chi2min << endl;
00680            if (chi2min < chi2cut)
00681              {
00682                if (debug_info) cout << "chi2 fine : " << chi2min << endl;
00683                TSOS UpdatedState= theUpdator->update( prSt, *bestHit );
00684                if (UpdatedState.isValid()){
00685                 hits.push_back(&(*bestHit));
00686                  traj.push( TM(prSt,UpdatedState, bestHit, chi2min) );
00687                 if (debug_info) edm::LogInfo("CosmicTrackFinder") <<
00688                    "STATE UPDATED WITH HIT AT POSITION "
00689                   
00690                                               << bestHit->globalPosition()
00691                                                <<UpdatedState<<" "
00692                                                <<traj.chiSquared();
00693                 if (debug_info) cout  <<
00694                    "STATE UPDATED WITH HIT AT POSITION "
00695                   
00696                                               << bestHit->globalPosition()
00697                                                <<UpdatedState<<" "
00698                                                <<traj.chiSquared();
00699                  if (debug_info) cout << "State is valid ..." << endl;
00700                 break; // now we need to 
00701                }
00702                else
00703                  {
00704                   edm::LogWarning("CosmicTrackFinder")<<" State can not be updated with hit at position " << endl;
00705                   TSOS UpdatedState= theUpdator->update( prSt, *bestHit );
00706                   if (UpdatedState.isValid()){
00707                     cout  <<
00708                       "NOT! UPDATED WITH HIT AT POSITION "
00709                       
00710                           << bestHit->globalPosition()
00711                           <<UpdatedState<<" "
00712                           <<traj.chiSquared();
00713                     
00714                   }
00715                 }
00716             } 
00717          }
00718      } //simple version end
00719      else 
00720      {
00721        //first sort the dets in the order they are traversed by the trajectory
00722        // we need three loops:
00723        // 1: loop as long as there can be an new hit added to the trajectory
00724        // 2: loop over all dets that might be hit
00725        // 3: loop over all hits on a certain det
00726        
00727        
00728        std::vector < std::pair<TrackingRecHitRangeIterator, TSOS> > trackHitCandidates;
00729        std::vector <std::pair<TrackingRecHitRangeIterator, TSOS> >::iterator iHitRange;
00730        std::vector <uint32_t> processedDets;
00731        do
00732         {
00733           
00734           //create vector of possibly hit detectors...
00735           trackHitCandidates.clear();      
00736           DetId currDet;
00737           for( TrackingRecHitRangeIterator iHit = hitRangeByDet.begin(); iHit != hitRangeByDet.end(); iHit++ )
00738             {
00739               const TrackingRecHit *currHit = *(iHit->first);
00740               currDet = currHit->geographicalId();
00741  
00742               if ( find(processedDets.begin(), processedDets.end(), currDet.rawId()) != processedDets.end() )
00743                 continue;
00744               
00745               TSOS prSt= currPropagator->propagate(traj.lastMeasurement().updatedState(),
00746                                                 tracker->idToDet(currDet)->surface());
00747               if ( ( !prSt.isValid() ) ||  (theEstimator->Chi2MeasurementEstimatorBase::estimate(prSt,tracker->idToDet(currDet)->surface() ) == false) )
00748  //           if ( ( !prSt.isValid() ) ||  (theEstimator->estimate(prSt,tracker->idToDet(currDet)->surface() ) == false) )  
00749                 continue;
00750      
00751               trackHitCandidates.push_back(  make_pair(iHit, prSt) );
00752             }
00753           
00754           if (!trackHitCandidates.size())
00755           break;
00756  
00757           if (debug_info) cout << Hits.size() << " (int) trackHitCandidates.begin() " << trackHitCandidates.size() << endl;
00758           if (debug_info) cout << "Before sorting ... " << endl; 
00759  
00760           if (debug_info)         
00761           for( iHitRange = trackHitCandidates.begin(); iHitRange != trackHitCandidates.end(); iHitRange++ )
00762             {
00763               if (debug_info) cout << (tracker->idToDet((*(iHitRange->first->first))->geographicalId()))->position();
00764             }
00765           if (debug_info) cout << endl;
00766           
00767  
00768           stable_sort( trackHitCandidates.begin(), trackHitCandidates.end(), CompareDetByTraj(traj.lastMeasurement().updatedState())  );
00769           
00770           if (debug_info) cout << "After sorting ... " << endl; 
00771           if (debug_info)
00772             {
00773             for( iHitRange = trackHitCandidates.begin(); iHitRange != trackHitCandidates.end(); iHitRange++ )
00774               {
00775                 if (debug_info) cout << (tracker->idToDet((*(iHitRange->first->first))->geographicalId()))->position();
00776               }
00777             cout << endl;
00778             }
00779  
00780         for( iHitRange = trackHitCandidates.begin(); iHitRange != trackHitCandidates.end(); iHitRange++ )      //loop over dets
00781           {
00782             
00783             //now find the best hit of the detector
00784             if (debug_info) cout << "loop2 " << trackHitCandidates.size()  <<" " << trackHitCandidates.end() - iHitRange << endl;
00785             const TrackingRecHit *currHit = *(iHitRange->first->first);
00786             
00787             TransientTrackingRecHit::RecHitPointer bestHit = RHBuilder->build( currHit );
00788             TSOS currPrSt = (*iHitRange).second;
00789         
00790             if (debug_info) cout << "curr position" << bestHit->globalPosition();
00791             for( TrackingRecHitIterator iHit = (*iHitRange).first->first+1; iHit != iHitRange->first->second; iHit++ )
00792               {
00793                 TransientTrackingRecHit::RecHitPointer tmpHit = RHBuilder->build( *iHit );
00794                 if (debug_info) cout << "curr position" << tmpHit->globalPosition() ;
00795           
00796               }
00797           }
00798         if (debug_info) cout << "Cross check end ..." << endl;
00799  
00800  
00801         //just a simple test if the same hit can be added twice ...
00802         //      for( iHitRange = trackHitCandidates.begin(); iHitRange != trackHitCandidates.end(); iHitRange++ )      //loop over all hits
00803         
00804         //      break;
00805         
00806         for( iHitRange = trackHitCandidates.begin(); iHitRange != trackHitCandidates.end(); iHitRange++ )      //loop over detsall hits
00807           {
00808             
00809             //now find the best hit of the detector
00810             if (debug_info) cout << "loop2 " << trackHitCandidates.size()  <<" " << trackHitCandidates.end() - iHitRange << endl;
00811             
00812             const TrackingRecHit *currHit = *(iHitRange->first->first);
00813  
00814             processedDets.push_back(currHit->geographicalId().rawId());
00815             
00816             
00817             TransientTrackingRecHit::RecHitPointer bestHit = RHBuilder->build( currHit );
00818  
00819             if (debug_info) cout << "curr position A" << bestHit->globalPosition() << endl;
00820             TSOS currPrSt = (*iHitRange).second;
00821             double chi2min = theEstimator->estimate( currPrSt, *bestHit).second;
00822  
00823             if (debug_info) cout << "Size " << iHitRange->first->second - (*iHitRange).first->first << endl; 
00824             for( TrackingRecHitIterator iHit = (*iHitRange).first->first+1; iHit != iHitRange->first->second; iHit++ )
00825               {
00826                 if (debug_info) cout << "loop3 " <<" "<< Hits.end() - iHit << endl;
00827               
00828                 TransientTrackingRecHit::RecHitPointer tmpHit = RHBuilder->build( *iHit );
00829                 if (debug_info) cout << "curr position B" << tmpHit->globalPosition() << endl;
00830                 double currChi2 = theEstimator->estimate(currPrSt, *tmpHit).second;
00831                 if ( currChi2 < chi2min )
00832                   {
00833                     if (debug_info) cout << "Is best hit" << endl;
00834                     chi2min = currChi2;
00835                     bestHit = tmpHit;
00836                   }
00837               }
00838             //now we have checked the det and can remove the entry from the vector...
00839           
00840             //if (debug_info) cout << "before erase ..." << endl;
00841             //this is to slow ...
00842             // hitRangeByDet.erase( (*iHitRange).first,(*iHitRange).first+1 );    
00843             //if (debug_info) cout << "after erase ..." << endl;
00844  
00845             if (debug_info) cout << chi2min << endl;
00846             //if the track can be added to the trajectory 
00847             if (chi2min < chi2cut)
00848               {
00849                 if (debug_info) cout << "chi2 fine : " << chi2min << endl;
00850  
00851                 //  if (debug_info) cout << "previaous state " << traj.lastMeasurement().updatedState() <<endl;
00852                 TSOS UpdatedState= theUpdator->update( currPrSt, *bestHit );
00853                 if (UpdatedState.isValid()){
00854  
00855                   hits.push_back(&(*bestHit));
00856                   traj.push( TM(currPrSt,UpdatedState, bestHit, chi2min) );
00857                   if (debug_info) edm::LogInfo("CosmicTrackFinder") <<
00858                     "STATE UPDATED WITH HIT AT POSITION "
00859                     //   <<tmphitbestdet->globalPosition()
00860                                                 <<UpdatedState<<" "
00861                                                 <<traj.chiSquared();
00862                   if (debug_info) cout << "Added Hit" << bestHit->globalPosition() << endl;
00863                   if (debug_info) cout << "State is valid ..." << UpdatedState << endl;
00864                   //cout << "updated state " << traj.lastMeasurement().updatedState() <<endl;
00865  
00866                   //          return; //break;
00867                   //
00868                   //          TSOS prSt= currPropagator->propagate(traj.lastMeasurement().updatedState(),
00869                   //                                          tracker->idToDet( bestHit->geographicalId() )->surface());
00870                   //      
00871                   //          if ( prSt.isValid())
00872                   //            cout << "the same hit can be added twice ..." << endl;  
00873                   //
00874                   
00875                   break;
00876                 }
00877                 else
00878                   {
00879                     if (debug_info) edm::LogWarning("CosmicTrackFinder")<<" State can not be updated with hit at position "
00880                                                         << bestHit->globalPosition();  
00881                     //          cout << "State can not be updated with hit at " << bestHit->globalPosition() << endl;
00882                   }
00883                 continue;
00884               }
00885             else
00886               {
00887                 //      cout << "chi2 to big : " << chi2min << endl;
00888               }
00889             if (debug_info) cout << " continue 1 " << endl;
00890           }
00891         //now we remove all already processed dets from the list ...
00892         // hitRangeByDet.erase( (*trackHitCandidates.begin()).first,(*iHitRange).first+1 );       
00893  
00894         if (debug_info) cout << " continue 2 " << endl;
00895        }
00896      //if this was the last exit
00897      while ( iHitRange != trackHitCandidates.end() );
00898      }
00899  
00900  
00901 }
00902 
00903 
00904 bool 
00905 CRackTrajectoryBuilder::qualityFilter(Trajectory traj){
00906   int ngoodhits=0;
00907   if(geometry=="MTCC"){
00908     std::vector< ConstReferenceCountingPointer< TransientTrackingRecHit> > hits= traj.recHits();
00909     std::vector< ConstReferenceCountingPointer< TransientTrackingRecHit> >::const_iterator hit;
00910     for(hit=hits.begin();hit!=hits.end();hit++){
00911       unsigned int iid=(*hit)->hit()->geographicalId().rawId();
00912       //CHECK FOR 3 hits r-phi
00913       if(((iid>>0)&0x3)!=1) ngoodhits++;
00914     }
00915   }
00916   else ngoodhits=traj.foundHits();
00917   
00918   if ( ngoodhits >= theMinHits) {
00919     return true;
00920   }
00921   else {
00922     return false;
00923   }
00924 }
00925 
00926 //----------------------------------------------------------------------------------------------------------
00927 // little helper function that returns false if both hits conatin the same information
00928 
00929 bool CRackTrajectoryBuilder::isDifferentStripReHit2D  (const SiStripRecHit2D& hitA, const  SiStripRecHit2D& hitB )
00930 {
00931   if ( hitA.geographicalId() != hitB.geographicalId() )
00932     return true;
00933   if ( hitA.localPosition().x() != hitB.localPosition().x() )
00934     return true;
00935   if ( hitA.localPosition().y() != hitB.localPosition().y() )
00936     return true;
00937   if ( hitA.localPosition().z() != hitB.localPosition().z() )
00938     return true;
00939 
00940   //  if (debug_info) cout << hitA.localPosition() << endl;
00941   //  if (debug_info) cout << hitB << endl;
00942 
00943   return false;
00944 }
00945 
00946 
00947 
00948 //----backfitting
00949 std::pair<TrajectoryStateOnSurface, const GeomDet*> 
00950 CRackTrajectoryBuilder::innerState( const Trajectory& traj) const
00951 {
00952   int lastFitted = 999;
00953   int nhits = traj.foundHits();
00954   if (nhits < lastFitted+1) lastFitted = nhits-1;
00955 
00956   std::vector<TrajectoryMeasurement> measvec = traj.measurements();
00957   TransientTrackingRecHit::ConstRecHitContainer firstHits;
00958 
00959   bool foundLast = false;
00960   int actualLast = -99;
00961   for (int i=lastFitted; i >= 0; i--) {
00962     if(measvec[i].recHit()->isValid()){
00963       if(!foundLast){
00964         actualLast = i; 
00965         foundLast = true;
00966       }
00967       firstHits.push_back( measvec[i].recHit());
00968     }
00969   }
00970   TSOS unscaledState = measvec[actualLast].updatedState();
00971   AlgebraicSymMatrix55 C=ROOT::Math::SMatrixIdentity();
00972   // C *= 100.;
00973 
00974   TSOS startingState( unscaledState.localParameters(), LocalTrajectoryError(C),
00975                       unscaledState.surface(),
00976                       thePropagator->magneticField());
00977 
00978   // cout << endl << "FitTester starts with state " << startingState << endl;
00979 
00980   KFTrajectoryFitter backFitter( *thePropagator,
00981                                  KFUpdator(),
00982                                  Chi2MeasurementEstimator( 100., 3));
00983 
00984   PropagationDirection backFitDirection = traj.direction() == alongMomentum ? oppositeToMomentum: alongMomentum;
00985 
00986   // only direction matters in this contest
00987   TrajectorySeed fakeSeed = TrajectorySeed(PTrajectoryStateOnDet() , 
00988                                            edm::OwnVector<TrackingRecHit>(),
00989                                            backFitDirection);
00990 
00991   vector<Trajectory> fitres = backFitter.fit( fakeSeed, firstHits, startingState);
00992 
00993   if (fitres.size() != 1) {
00994     // cout << "FitTester: first hits fit failed!" << endl;
00995     return std::pair<TrajectoryStateOnSurface, const GeomDet*>();
00996   }
00997 
00998   TrajectoryMeasurement firstMeas = fitres[0].lastMeasurement();
00999   TSOS firstState = firstMeas.updatedState();
01000 
01001   //  cout << "FitTester: Fitted first state " << firstState << endl;
01002   //cout << "FitTester: chi2 = " << fitres[0].chiSquared() << endl;
01003 
01004   TSOS initialState( firstState.localParameters(), LocalTrajectoryError(C),
01005                      firstState.surface(),
01006                      thePropagator->magneticField());
01007 
01008   return std::pair<TrajectoryStateOnSurface, const GeomDet*>( initialState, 
01009                                                               firstMeas.recHit()->det());
01010 }