CMS 3D CMS Logo

/data/refman/pasoursint/CMSSW_4_4_5_patch3/src/RecoMuon/MuonSeedGenerator/src/MuonCSCSeedFromRecHits.cc

Go to the documentation of this file.
00001 #include "RecoMuon/MuonSeedGenerator/src/MuonCSCSeedFromRecHits.h"
00002 #include "RecoMuon/MuonSeedGenerator/src/MuonSeedPtExtractor.h"
00003 #include "DataFormats/MuonDetId/interface/CSCDetId.h"
00004 #include "Geometry/CSCGeometry/interface/CSCChamberSpecs.h"
00005 #include "RecoMuon/TrackingTools/interface/MuonPatternRecoDumper.h"
00006 #include "DataFormats/TrackingRecHit/interface/TrackingRecHit.h"
00007 #include "DataFormats/TrajectoryState/interface/PTrajectoryStateOnDet.h"
00008 #include "DataFormats/Math/interface/deltaPhi.h"
00009 #include "TrackingTools/TrajectoryState/interface/TrajectoryStateTransform.h"
00010 #include "FWCore/MessageLogger/interface/MessageLogger.h"
00011 #include "Geometry/CSCGeometry/interface/CSCChamberSpecs.h"
00012 #include <iomanip>
00013 
00014 
00015 MuonCSCSeedFromRecHits::MuonCSCSeedFromRecHits()
00016 : MuonSeedFromRecHits()
00017 {
00018 }
00019 
00020 
00021 TrajectorySeed MuonCSCSeedFromRecHits::seed() const
00022 {
00023   TrajectorySeed result;
00024   if(theRhits.size() == 1) 
00025   {
00026      //return createSeed(100., 100., theRhits[0]);
00027      makeDefaultSeed(result);
00028      return result;
00029   }
00030   //@@ doesn't handle overlap between ME11 and ME12 correctly
00031   // sort by station
00032   MuonRecHitContainer station1Hits, station2Hits, station3Hits, station4Hits;
00033   for ( MuonRecHitContainer::const_iterator iter = theRhits.begin(), end = theRhits.end();
00034         iter != end; ++iter)
00035   {
00036     int station = CSCDetId((*iter)->geographicalId().rawId()).station();
00037     if(station == 1)
00038     {
00039       station1Hits.push_back(*iter);
00040     }
00041     else if(station == 2) 
00042     {
00043       station2Hits.push_back(*iter);
00044     }
00045     else if(station == 3)
00046     {
00047       station3Hits.push_back(*iter);
00048     }
00049     else if(station == 4)
00050     {
00051       station4Hits.push_back(*iter);
00052     }
00053   }
00054 
00055   //std::cout << "Station hits " << station1Hits.size() << " " 
00056   //                            << station2Hits.size() << " "
00057   //                             << station3Hits.size() << std::endl;
00058 
00059   // see whether station 2 or station 3 is better
00060   MuonRecHitContainer * betterSecondHits = &station2Hits; 
00061   MuonRecHitContainer * notAsGoodSecondHits = &station3Hits;
00062   if(!station2Hits.empty() && !station3Hits.empty())
00063   { 
00064     // swap if station 3 has better quailty
00065     if(segmentQuality(station3Hits[0]) < segmentQuality(station2Hits[0]))
00066     {
00067       betterSecondHits = &station3Hits;
00068       notAsGoodSecondHits = &station2Hits; 
00069     }
00070   }
00071 
00072   // now try to make pairs
00073   if(makeSeed(station1Hits, *betterSecondHits, result))
00074   {
00075     return result;
00076   }
00077   if(makeSeed(station1Hits, *notAsGoodSecondHits, result))
00078   {
00079     return result;
00080   }
00081   if(makeSeed(station2Hits, station3Hits, result))
00082   {
00083     return result;
00084   }
00085   if(makeSeed(station1Hits, station4Hits, result))
00086   {
00087     return result;
00088   }
00089 
00090 
00091 
00092   // no luck
00093   makeDefaultSeed(result);
00094   return result;
00095 }
00096 
00097 
00098 bool MuonCSCSeedFromRecHits::makeSeed(const MuonRecHitContainer & hits1, const MuonRecHitContainer & hits2,
00099                                       TrajectorySeed & seed) const
00100 {
00101   for ( MuonRecHitContainer::const_iterator itr1 = hits1.begin(), end1 = hits1.end();
00102         itr1 != end1; ++itr1)
00103   {
00104     CSCDetId cscId1((*itr1)->geographicalId().rawId());
00105     //int type1 = CSCChamberSpecs::whatChamberType(cscId1.station(), cscId1.ring());
00106 
00107     for ( MuonRecHitContainer::const_iterator itr2 = hits2.begin(), end2 = hits2.end();
00108           itr2 != end2; ++itr2)
00109     {
00110 
00111       CSCDetId cscId2((*itr2)->geographicalId().rawId());
00112       //int type2 = CSCChamberSpecs::whatChamberType(cscId2.station(), cscId2.ring());
00113 
00114         // take the first pair that comes along.  Probably want to rank them later
00115       std::vector<double> pts = thePtExtractor->pT_extract(*itr1, *itr2);
00116         
00117         double pt = pts[0];
00118         double sigmapt = pts[1];
00119         double minpt = 3.;
00120 
00121         // if too small, probably an error.  Keep trying.
00122         if(fabs(pt) > minpt)
00123         {
00124           double maxpt = 2000.;
00125           if(pt > maxpt) {
00126             pt = maxpt;
00127             sigmapt = maxpt;
00128           }
00129           if(pt < -maxpt) {
00130             pt = -maxpt;
00131             sigmapt = maxpt;
00132           }
00133 
00134           // get the position and direction from the higher-quality segment
00135           ConstMuonRecHitPointer bestSeg = bestEndcapHit(theRhits);
00136           seed = createSeed(pt, sigmapt, bestSeg);
00137 
00138           //std::cout << "FITTED TIMESPT " << pt << " dphi " << dphi << " eta " << eta << std::endl;
00139           return true;
00140         }
00141 
00142     }
00143   }
00144 
00145   // guess it didn't find one
00146 //std::cout << "NOTHING FOUND ! " << std::endl;
00147   return false;
00148 }
00149 
00150 
00151 //typedef MuonTransientTrackingRecHit::MuonRecHitContainer MuonRecHitContainer;
00152 int MuonCSCSeedFromRecHits::segmentQuality(ConstMuonRecHitPointer  segment) const
00153 {
00154   int Nchi2 = 0;
00155   int quality = 0;
00156   int nhits = segment->recHits().size();
00157   if ( segment->chi2()/(nhits*2.-4.) > 3. ) Nchi2 = 1;
00158   if ( segment->chi2()/(nhits*2.-4.) > 9. ) Nchi2 = 2;
00159 
00160   if ( nhits >  4 ) quality = 1 + Nchi2;
00161   if ( nhits == 4 ) quality = 3 + Nchi2;
00162   if ( nhits == 3 ) quality = 5 + Nchi2;
00163 
00164   float dPhiGloDir = fabs ( deltaPhi(segment->globalPosition().phi(), segment->globalDirection().phi()) );
00165 
00166   if ( dPhiGloDir > .2 ) ++quality;
00167   // add a penalty for being ME1A
00168   if(segment->isCSC() && CSCDetId(segment->geographicalId()).ring() == 4) ++quality;
00169   return quality;
00170 }
00171 
00172 
00173 
00174 MuonCSCSeedFromRecHits::ConstMuonRecHitPointer
00175 MuonCSCSeedFromRecHits::bestEndcapHit(const MuonRecHitContainer & endcapHits) const
00176 {
00177   MuonRecHitPointer me1=0, meit=0;
00178   float dPhiGloDir = .0;                            //  +v
00179   float bestdPhiGloDir = M_PI;                      //  +v
00180   int quality1 = 0, quality = 0;        //  +v  I= 5,6-p. / II= 4p.  / III= 3p.
00181 
00182   for ( MuonRecHitContainer::const_iterator iter = endcapHits.begin(); iter!= endcapHits.end(); iter++ ){
00183     if ( !(*iter)->isCSC() ) continue;
00184 
00185     // tmp compar. Glob-Dir for the same tr-segm:
00186 
00187     meit = *iter;
00188 
00189     quality = segmentQuality(meit);
00190 
00191     dPhiGloDir = fabs ( deltaPhi(meit->globalPosition().phi(), meit->globalDirection().phi()) );
00192 
00193     if(!me1){
00194       me1 = meit;
00195       quality1 = quality;
00196       bestdPhiGloDir = dPhiGloDir;
00197     }
00198 
00199     if(me1) {
00200 
00201       if ( !me1->isValid() ) {
00202         me1 = meit;
00203         quality1 = quality;
00204         bestdPhiGloDir = dPhiGloDir;
00205       }
00206 
00207       if ( me1->isValid() && quality < quality1 ) {
00208         me1 = meit;
00209         quality1 = quality;
00210         bestdPhiGloDir = dPhiGloDir;
00211       }
00212 
00213       if ( me1->isValid() && bestdPhiGloDir > .03 ) {
00214         if ( dPhiGloDir < bestdPhiGloDir - .01 && quality == quality1 ) {
00215           me1 = meit;
00216           quality1 = quality;
00217           bestdPhiGloDir = dPhiGloDir;
00218         }
00219       }
00220     }
00221 
00222   }   //  iter
00223 
00224   return me1;
00225 }
00226 
00227 
00228 void MuonCSCSeedFromRecHits::makeDefaultSeed(TrajectorySeed & seed) const
00229 {
00230   //Search ME1  ...
00231   ConstMuonRecHitPointer me1= bestEndcapHit(theRhits);
00232   bool good=false;
00233 
00234   if(me1 && me1->isValid() )
00235   {
00236     good = createDefaultEndcapSeed(me1, seed); 
00237   }
00238 }
00239 
00240 
00241 
00242 
00243 
00244 bool 
00245 MuonCSCSeedFromRecHits::createDefaultEndcapSeed(ConstMuonRecHitPointer last, 
00246                                  TrajectorySeed & seed) const {
00247   //float momentum = computeDefaultPt(last);
00248   std::vector<double> momentum = thePtExtractor->pT_extract(last, last);
00249   seed = createSeed(momentum[0],momentum[1],last);
00250   return true;
00251 }
00252 
00253 
00254 
00255 void MuonCSCSeedFromRecHits::analyze() const 
00256 {
00257   for ( MuonRecHitContainer::const_iterator iter = theRhits.begin(); iter!= theRhits.end(); iter++ ){
00258     if ( !(*iter)->isCSC() ) continue;
00259     for ( MuonRecHitContainer::const_iterator iter2 = iter + 1; iter2 != theRhits.end(); ++iter2)
00260     {
00261       if( !(*iter2)->isCSC() ) continue;
00262 
00263       CSCDetId cscId1((*iter)->geographicalId().rawId());
00264       CSCDetId cscId2((*iter2)->geographicalId().rawId());
00265       double dphi = deltaPhi((**iter).globalPosition().phi(), (**iter2).globalPosition().phi());
00266 
00267       int type1 = cscId1.iChamberType();
00268       int type2 = cscId2.iChamberType();
00269 
00270       // say the lower station first
00271       if(type1 < type2)
00272       {
00273         std::cout << "HITPAIRA," << type1 << type2 << "," <<
00274             dphi << "," << (**iter).globalPosition().eta() << std::endl;
00275       }
00276       if(type2 < type1)
00277       {
00278         std::cout << "HITPAIRB," << type2 << type1 << "," <<
00279             -dphi << "," << (**iter2).globalPosition().eta() << std::endl;
00280       }
00281       if(type1 == type2)
00282       {
00283         std::cout << "HITPAIRSAMESTATION," << type1 << cscId1.ring() << cscId2.ring()
00284            << "," << dphi << "," << (**iter).globalPosition().eta() << std::endl;
00285       }
00286 
00287     }
00288   }
00289 }