00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046
00047
00048
00049
00050
00051
00052
00053
00054
00055 #include <vector>
00056 #include <iostream>
00057 #include <cmath>
00058
00059 #include "RoadSearchCloudMakerAlgorithm.h"
00060
00061 #include "FWCore/ServiceRegistry/interface/Service.h"
00062
00063 #include "DataFormats/Common/interface/Handle.h"
00064 #include "FWCore/Framework/interface/ESHandle.h"
00065 #include "FWCore/Framework/interface/EventSetup.h"
00066 #include "FWCore/MessageLogger/interface/MessageLogger.h"
00067
00068 #include "DataFormats/Common/interface/Ref.h"
00069 #include "DataFormats/RoadSearchSeed/interface/RoadSearchSeedCollection.h"
00070 #include "DataFormats/RoadSearchCloud/interface/RoadSearchCloud.h"
00071 #include "DataFormats/TrackerRecHit2D/interface/SiStripRecHit2D.h"
00072 #include "DataFormats/TrackingRecHit/interface/TrackingRecHit.h"
00073 #include "DataFormats/SiStripDetId/interface/StripSubdetector.h"
00074 #include "DataFormats/SiPixelDetId/interface/PixelSubdetector.h"
00075 #include "DataFormats/SiStripDetId/interface/TIBDetId.h"
00076 #include "DataFormats/SiStripDetId/interface/TOBDetId.h"
00077 #include "DataFormats/SiStripDetId/interface/TIDDetId.h"
00078 #include "DataFormats/SiStripDetId/interface/TECDetId.h"
00079 #include "DataFormats/SiPixelDetId/interface/PXBDetId.h"
00080 #include "DataFormats/SiPixelDetId/interface/PXFDetId.h"
00081
00082 #include "Geometry/CommonDetUnit/interface/GeomDetUnit.h"
00083 #include "Geometry/Records/interface/TrackerDigiGeometryRecord.h"
00084 #include "DataFormats/GeometryVector/interface/GlobalPoint.h"
00085 #include "DataFormats/GeometryVector/interface/LocalPoint.h"
00086 #include "Geometry/CommonTopologies/interface/TrapezoidalStripTopology.h"
00087 #include "Geometry/CommonTopologies/interface/RectangularStripTopology.h"
00088
00089 #include "DataFormats/SiPixelDigi/interface/PixelDigi.h"
00090 #include "Geometry/CommonTopologies/interface/PixelTopology.h"
00091
00092 #include "TrackingTools/RoadSearchHitAccess/interface/RoadSearchDetIdHelper.h"
00093
00094 #include "RecoTracker/RoadMapRecord/interface/RoadMapRecord.h"
00095
00096 #include "RecoLocalTracker/SiStripRecHitConverter/interface/SiStripRecHitMatcher.h"
00097 #include "Geometry/TrackerGeometryBuilder/interface/GluedGeomDet.h"
00098
00099 using namespace std;
00100
00101 double RoadSearchCloudMakerAlgorithm::epsilon = 0.000000001;
00102
00103 RoadSearchCloudMakerAlgorithm::RoadSearchCloudMakerAlgorithm(const edm::ParameterSet& conf) : conf_(conf) {
00104 recHitVectorClass.setMode(DetHitAccess::standard);
00105 recHitVectorClass.use_rphiRecHits(conf_.getParameter<bool>("UseRphiRecHits"));
00106 recHitVectorClass.use_stereoRecHits(conf_.getParameter<bool>("UseStereoRecHits"));
00107
00108
00109 theRPhiRoadSize = conf_.getParameter<double>("RPhiRoadSize");
00110 theZPhiRoadSize = conf_.getParameter<double>("ZPhiRoadSize");
00111 UsePixels = conf_.getParameter<bool>("UsePixelsinRS");
00112 NoFieldCosmic = conf_.getParameter<bool>("StraightLineNoBeamSpotCloud");
00113 theMinimumHalfRoad = conf_.getParameter<double>("MinimumHalfRoad");
00114
00115 maxDetHitsInCloudPerDetId = conf_.getParameter<unsigned int>("MaxDetHitsInCloudPerDetId");
00116 minFractionOfUsedLayersPerCloud = conf_.getParameter<double>("MinimalFractionOfUsedLayersPerCloud");
00117 maxFractionOfMissedLayersPerCloud = conf_.getParameter<double>("MaximalFractionOfMissedLayersPerCloud");
00118 maxFractionOfConsecutiveMissedLayersPerCloud = conf_.getParameter<double>("MaximalFractionOfConsecutiveMissedLayersPerCloud");
00119 increaseMaxNumberOfConsecutiveMissedLayersPerCloud = conf_.getParameter<unsigned int>("IncreaseMaxNumberOfConsecutiveMissedLayersPerCloud");
00120 increaseMaxNumberOfMissedLayersPerCloud = conf_.getParameter<unsigned int>("IncreaseMaxNumberOfMissedLayersPerCloud");
00121
00122 doCleaning_ = conf.getParameter<bool>("DoCloudCleaning");
00123 mergingFraction_ = conf.getParameter<double>("MergingFraction");
00124 maxRecHitsInCloud_ = (unsigned int)conf.getParameter<int>("MaxRecHitsInCloud");
00125 scalefactorRoadSeedWindow_ = conf.getParameter<double>("scalefactorRoadSeedWindow");
00126
00127 roadsLabel_ = conf.getParameter<std::string>("RoadsLabel");
00128
00129 }
00130
00131 RoadSearchCloudMakerAlgorithm::~RoadSearchCloudMakerAlgorithm() {
00132
00133 }
00134
00135 double RoadSearchCloudMakerAlgorithm::map_phi(double phi) {
00136
00137 double result = phi;
00138 if ( result < -1.0*Geom::twoPi()) result = result + Geom::twoPi();
00139 if ( result < 0) result = Geom::twoPi() + result;
00140 if ( result > Geom::twoPi()) result = result - Geom::twoPi();
00141 return result;
00142 }
00143
00144 double RoadSearchCloudMakerAlgorithm::map_phi2(double phi) {
00145
00146 double result = phi;
00147 if ( result < 1.0*Geom::pi() ) result = result + Geom::twoPi();
00148 if ( result >= Geom::pi()) result = result - Geom::twoPi();
00149 return result;
00150 }
00151
00152 void RoadSearchCloudMakerAlgorithm::run(edm::Handle<RoadSearchSeedCollection> input,
00153 const SiStripRecHit2DCollection* rphiRecHits,
00154 const SiStripRecHit2DCollection* stereoRecHits,
00155 const SiStripMatchedRecHit2DCollection* matchedRecHits,
00156 const SiPixelRecHitCollection *pixRecHits,
00157 const edm::EventSetup& es,
00158 RoadSearchCloudCollection &output)
00159 {
00160
00161 const int nphibin = 24;
00162 const int netabin = 24;
00163 RoadSearchCloudCollection CloudArray[nphibin][netabin];
00164
00165
00166 edm::ESHandle<Roads> roads;
00167 es.get<RoadMapRecord>().get(roadsLabel_, roads);
00168
00169
00170 const RoadSearchSeedCollection* inputSeeds = input.product();
00171
00172
00173 recHitVectorClass.setCollections(rphiRecHits,stereoRecHits,matchedRecHits,pixRecHits);
00174 recHitVectorClass.setMode(DetHitAccess::standard);
00175
00176
00177 edm::ESHandle<TrackerGeometry> tracker;
00178 es.get<TrackerDigiGeometryRecord>().get(tracker);
00179
00180
00181 SiStripRecHitMatcher* theHitMatcher = new SiStripRecHitMatcher(3.0);
00182
00183 edm::LogInfo("RoadSearch") << "Found " << inputSeeds->size() << " input seeds.";
00184
00185 for ( RoadSearchSeedCollection::const_iterator seed = inputSeeds->begin(); seed != inputSeeds->end(); ++seed) {
00186
00187 const Roads::RoadSeed *roadSeed = seed->getSeed();
00188
00189 if ( roadSeed == 0 ) {
00190 edm::LogWarning("RoadSearch") << "RoadSeed could not be resolved from RoadSearchSeed hits, discard seed!";
00191 } else {
00192
00193 Roads::type roadType = roads->getRoadType(roadSeed);
00194 if (NoFieldCosmic) roadType = Roads::RPhi;
00195
00196
00197
00198
00199
00200 const TrackingRecHit* innerSeedRingHit = (*(seed->begin()));
00201 const TrackingRecHit* outerSeedRingHit = (*(seed->end() - 1));
00202
00203 GlobalPoint innerSeedHitGlobalPosition = tracker->idToDet(innerSeedRingHit->geographicalId())->surface().toGlobal(innerSeedRingHit->localPosition());
00204 GlobalPoint outerSeedHitGlobalPosition = tracker->idToDet(outerSeedRingHit->geographicalId())->surface().toGlobal(outerSeedRingHit->localPosition());
00205
00206 LogDebug("RoadSearch") << "Seed # " <<seed-inputSeeds->begin() << " inner hit (x/y/z): "
00207 << innerSeedHitGlobalPosition.x() << " / "
00208 << innerSeedHitGlobalPosition.y() << " / "
00209 << innerSeedHitGlobalPosition.z();
00210 LogDebug("RoadSearch") << "Seed # " <<seed-inputSeeds->begin() << " outer hit (x/y/z): "
00211 << outerSeedHitGlobalPosition.x() << " / "
00212 << outerSeedHitGlobalPosition.y() << " / "
00213 << outerSeedHitGlobalPosition.z();
00214
00215 LogDebug("RoadSearch") << "Seed # " <<seed-inputSeeds->begin() << " inner hit (r/phi): "
00216 << innerSeedHitGlobalPosition.perp() << " / "
00217 << innerSeedHitGlobalPosition.phi();
00218 LogDebug("RoadSearch") << "Seed # " <<seed-inputSeeds->begin() << " outer hit (r/phi): "
00219 << outerSeedHitGlobalPosition.perp() << " / "
00220 << outerSeedHitGlobalPosition.phi();
00221
00222
00223
00224 double d0 = 0.0;
00225 double phi0 = -99.;
00226 double k0 = -99999999.99;
00227
00228 double phi1 = -99.;
00229 double k1 = -99999999.99;
00230
00231
00232 double outer_phi = map_phi(outerSeedHitGlobalPosition.phi());
00233 double outer_eta = outerSeedHitGlobalPosition.eta();
00234
00235 int phibin = (int)(nphibin*(outer_phi/(2*Geom::pi())));
00236 int etabin = (int)(netabin*(outer_eta+3.0)/6.0);
00237
00238
00239 if ( roadType == Roads::RPhi ) {
00240 double dr = outerSeedHitGlobalPosition.perp() - innerSeedHitGlobalPosition.perp();
00241 const double dr_min = 1;
00242 if ( dr < dr_min ) {
00243 edm::LogWarning("RoadSearch") << "RPhi road: seed Hits distance smaller than 1 cm, do not consider this seed.";
00244 } else {
00245
00246 double det = innerSeedHitGlobalPosition.x() * outerSeedHitGlobalPosition.y() - innerSeedHitGlobalPosition.y() * outerSeedHitGlobalPosition.x();
00247 if ( det == 0 ) {
00248 edm::LogWarning("RoadSearch") << "RPhi road: 'det' == 0, do not consider this seed.";
00249 } else {
00250 double x0=0.0; double y0=0.0;
00251 double innerx=innerSeedHitGlobalPosition.x();
00252 double innery=innerSeedHitGlobalPosition.y();
00253 double outerx=outerSeedHitGlobalPosition.x();
00254 double outery=outerSeedHitGlobalPosition.y();
00255
00256 if (NoFieldCosmic){
00257 phi0=atan2(outery-innery,outerx-innerx);
00258 double alpha=atan2(innery,innerx);
00259 double d1=sqrt(innerx*innerx+innery*innery);
00260 d0=d1*sin(alpha-phi0); x0=-d0*sin(phi0); y0=d0*cos(phi0); k0=0.0;
00261 }else{
00262 makecircle(innerx,innery,outerx,outery,x0,y0);
00263 phi0 = phi0h;
00264 k0 = omegah;
00265 }
00266 LogDebug("RoadSearch") << "Seed # " <<seed-inputSeeds->begin() << " trajectory parameters: d0 = "<< d0 << " phi0 = " << phi0;
00267 }
00268 }
00269 } else {
00270 double dz = outerSeedHitGlobalPosition.z() - innerSeedHitGlobalPosition.z();
00271 const double dz_min = 1.e-6;
00272 if ( std::abs(dz) < dz_min ) {
00273 edm::LogWarning("RoadSearch") << "ZPhi road: seed Hits are less than .01 microns away in z, do not consider this seed.";
00274 } else {
00275
00276 k0 = map_phi2(outerSeedHitGlobalPosition.phi() - innerSeedHitGlobalPosition.phi()) / dz;
00277 phi0 = map_phi(innerSeedHitGlobalPosition.phi() - k0 * innerSeedHitGlobalPosition.z());
00278
00279
00280 makecircle(innerSeedHitGlobalPosition.x(),innerSeedHitGlobalPosition.y(),
00281 outerSeedHitGlobalPosition.x(),outerSeedHitGlobalPosition.y(),
00282 0.0,0.0);
00283 phi1 = phi0h;
00284 k1 = omegah;
00285 }
00286 }
00287
00288
00289 if ( (phi0 != -99.) && (k0 != -99999999.99) ) {
00290 const Roads::RoadSet *roadSet = seed->getSet();
00291
00292
00293 RoadSearchCloud cloud;
00294
00295 bool firstHitFound = false;
00296 unsigned int layerCounter = 0;
00297 unsigned int usedLayers = 0;
00298 unsigned int missedLayers = 0;
00299 unsigned int consecutiveMissedLayers = 0;
00300
00301 unsigned int totalLayers = roadSet->size();
00302
00303
00304
00305 unsigned int minNumberOfUsedLayersPerCloud = static_cast<unsigned int>(totalLayers * minFractionOfUsedLayersPerCloud + 0.5);
00306 if (minNumberOfUsedLayersPerCloud < 3) minNumberOfUsedLayersPerCloud = 3;
00307 unsigned int maxNumberOfMissedLayersPerCloud = static_cast<unsigned int>(totalLayers * maxFractionOfMissedLayersPerCloud + 0.5);
00308 unsigned int maxNumberOfConsecutiveMissedLayersPerCloud = static_cast<unsigned int>(totalLayers * maxFractionOfConsecutiveMissedLayersPerCloud + 0.5);
00309
00310
00311 if (std::abs(outer_eta) > 0.9 && std::abs(outer_eta) < 1.5) {
00312 maxNumberOfConsecutiveMissedLayersPerCloud += increaseMaxNumberOfConsecutiveMissedLayersPerCloud;
00313 maxNumberOfMissedLayersPerCloud += increaseMaxNumberOfMissedLayersPerCloud;
00314 }
00315
00316 for ( Roads::RoadSet::const_iterator roadSetVector = roadSet->begin();
00317 roadSetVector != roadSet->end();
00318 ++roadSetVector ) {
00319
00320 ++layerCounter;
00321 unsigned int usedHitsInThisLayer = 0;
00322 bool intersectsLayer = false;
00323
00324 for ( std::vector<const Ring*>::const_iterator ring = roadSetVector->begin(); ring != roadSetVector->end(); ++ring ) {
00325
00326
00327
00328 double ringRadius = (*ring)->getrmin() + ((*ring)->getrmax()-(*ring)->getrmin())/2;
00329 double ringZ = (*ring)->getzmin() + ((*ring)->getzmax()-(*ring)->getzmin())/2;
00330 double ringPhi = 0.0;
00331 if ( roadType == Roads::RPhi ) {
00332 ringPhi = phiFromExtrapolation(d0,phi0,k0,ringRadius,roadType);
00333 } else {
00334 ringPhi = phiFromExtrapolation(d0,phi0,k0,ringZ,roadType);
00335 }
00336 if (ringPhi == -99) continue;
00337 intersectsLayer = true;
00338
00339 LogDebug("RoadSearch") << "Seed # " <<seed-inputSeeds->begin() << " testing ring at R = " << ringRadius
00340 << " Z = " << ringZ << " ringPhi = " << ringPhi;
00341
00342 int nDetIds = (*ring)->getNumDetIds();
00343 double theHalfRoad = theMinimumHalfRoad*(2.0*Geom::pi())/((double)nDetIds);
00344
00345 double upperPhiRangeBorder = map_phi2(ringPhi + theHalfRoad);
00346 double lowerPhiRangeBorder = map_phi2(ringPhi - theHalfRoad);
00347
00348 if ( lowerPhiRangeBorder <= upperPhiRangeBorder ) {
00349
00350 for ( Ring::const_iterator detid = (*ring)->lower_bound(lowerPhiRangeBorder); detid != (*ring)->upper_bound(upperPhiRangeBorder); ++detid) {
00351 usedHitsInThisLayer += FillRecHitsIntoCloudGeneral(detid->second,d0,phi0,k0,phi1,k1,roadType,ringPhi,
00352 tracker.product(),theHitMatcher,cloud);
00353 }
00354
00355 } else {
00356 for ( Ring::const_iterator detid = (*ring)->lower_bound(lowerPhiRangeBorder); detid != (*ring)->end(); ++detid) {
00357 usedHitsInThisLayer += FillRecHitsIntoCloudGeneral(detid->second,d0,phi0,k0,phi1,k1,roadType,ringPhi,
00358 tracker.product(),theHitMatcher,cloud);
00359 }
00360
00361 for ( Ring::const_iterator detid = (*ring)->begin(); detid != (*ring)->upper_bound(upperPhiRangeBorder); ++detid) {
00362 usedHitsInThisLayer += FillRecHitsIntoCloudGeneral(detid->second,d0,phi0,k0,phi1,k1,roadType,ringPhi,
00363 tracker.product(),theHitMatcher,cloud);
00364 }
00365 }
00366 LogDebug("RoadSearch") << "Seed # " <<seed-inputSeeds->begin() << " now has " << usedHitsInThisLayer << " hits in ring at R = " << ringRadius
00367 << " Z = " << ringZ << " ringPhi = " << ringPhi;
00368 }
00369
00370 if ( !firstHitFound ) {
00371 if ( usedHitsInThisLayer > 0 ) {
00372
00373 firstHitFound = true;
00374
00375
00376 totalLayers = roadSet->size() - layerCounter + 1;
00377
00378
00379
00380 minNumberOfUsedLayersPerCloud = static_cast<unsigned int>(totalLayers * minFractionOfUsedLayersPerCloud + 0.5);
00381 if (minNumberOfUsedLayersPerCloud < 3) minNumberOfUsedLayersPerCloud = 3;
00382 maxNumberOfMissedLayersPerCloud = static_cast<unsigned int>(totalLayers * maxFractionOfMissedLayersPerCloud + 0.5);
00383 maxNumberOfConsecutiveMissedLayersPerCloud = static_cast<unsigned int>(totalLayers * maxFractionOfConsecutiveMissedLayersPerCloud + 0.5);
00384
00385
00386 if (std::abs(outer_eta) > 0.9 && std::abs(outer_eta) < 1.5) {
00387 maxNumberOfConsecutiveMissedLayersPerCloud += increaseMaxNumberOfConsecutiveMissedLayersPerCloud;
00388 maxNumberOfMissedLayersPerCloud += increaseMaxNumberOfMissedLayersPerCloud;
00389 }
00390
00391 ++usedLayers;
00392 consecutiveMissedLayers = 0;
00393
00394 }
00395 } else {
00396 if (intersectsLayer){
00397 if ( usedHitsInThisLayer > 0 ) {
00398 ++usedLayers;
00399 consecutiveMissedLayers = 0;
00400 } else {
00401 ++ missedLayers;
00402 ++consecutiveMissedLayers;
00403 }
00404 }
00405 LogDebug("RoadSearch") << "Seed # "<<seed-inputSeeds->begin() << " Layer info: "
00406 << " totalLayers: " << totalLayers
00407 << " usedLayers: " << usedLayers
00408 << " missedLayers: " << missedLayers
00409 << " consecutiveMissedLayers: " << consecutiveMissedLayers;
00410
00411
00412 if ( consecutiveMissedLayers > maxNumberOfConsecutiveMissedLayersPerCloud ) {
00413 LogDebug("RoadSearch") << "BREAK: seed # "<<seed-inputSeeds->begin()
00414 << " More than " << maxNumberOfConsecutiveMissedLayersPerCloud << " missed consecutive layers!";
00415 break;
00416 }
00417
00418
00419 if ( missedLayers > maxNumberOfMissedLayersPerCloud ) {
00420 LogDebug("RoadSearch") << "BREAK: seed # "<<seed-inputSeeds->begin()
00421 << " More than " << maxNumberOfMissedLayersPerCloud << " missed layers!";
00422 break;
00423 }
00424
00425
00426 if ( totalLayers-missedLayers < minNumberOfUsedLayersPerCloud ) {
00427 LogDebug("RoadSearch") << "BREAK: seed # "<<seed-inputSeeds->begin()
00428 << " Cannot satisfy at least " << minNumberOfUsedLayersPerCloud << " used layers!";
00429 break;
00430 }
00431 }
00432
00433 }
00434
00435 if ( consecutiveMissedLayers <= maxNumberOfConsecutiveMissedLayersPerCloud ) {
00436 if ( usedLayers >= minNumberOfUsedLayersPerCloud ) {
00437 if ( missedLayers <= maxNumberOfMissedLayersPerCloud ) {
00438
00439 CloudArray[phibin][etabin].push_back(cloud);
00440
00441 if ( roadType == Roads::RPhi ){
00442 LogDebug("RoadSearch") << "This r-phi seed # "<<seed-inputSeeds->begin()
00443 <<" yields a cloud with " <<cloud.size() <<" hits on " << usedLayers << " layers out of " << totalLayers;
00444 } else {
00445 LogDebug("RoadSearch") << "This z-phi seed # "<<seed-inputSeeds->begin()
00446 <<" yields a cloud with " <<cloud.size() <<" hits on " << usedLayers << " layers out of " << totalLayers;
00447 }
00448 } else {
00449 LogDebug("RoadSearch") << "Missed layers: " << missedLayers << " More than " << maxNumberOfMissedLayersPerCloud << " missed layers!";
00450 if ( roadType == Roads::RPhi ){
00451 LogDebug("RoadSearch") << "This r-phi seed # "<<seed-inputSeeds->begin() <<" yields no clouds";
00452 } else {
00453 LogDebug("RoadSearch") << "This z-phi seed # "<<seed-inputSeeds->begin() <<" yields no clouds";
00454 }
00455 }
00456 }
00457 else {
00458 LogDebug("RoadSearch") << "Seed # "<<seed-inputSeeds->begin() <<" fails: used layers = " << usedLayers << " < " << minNumberOfUsedLayersPerCloud;
00459 }
00460 }
00461 else {
00462 LogDebug("RoadSearch") << "Seed # "<<seed-inputSeeds->begin() <<" fails: consecutive missed layers = " << consecutiveMissedLayers << " > " << maxNumberOfConsecutiveMissedLayersPerCloud;
00463 }
00464 }
00465 }
00466 }
00467
00468
00469 for (int iphi=0; iphi<nphibin; ++iphi){
00470 for (int ieta=0; ieta<netabin; ++ieta){
00471 if (!CloudArray[iphi][ieta].empty()) {
00472 if (doCleaning_){
00473 RoadSearchCloudCollection temp = Clean(&CloudArray[iphi][ieta]);
00474 for ( RoadSearchCloudCollection::const_iterator ic = temp.begin(); ic!=temp.end(); ++ic)
00475 output.push_back(*ic);
00476 }
00477 else
00478 for ( RoadSearchCloudCollection::const_iterator ic = CloudArray[iphi][ieta].begin();
00479 ic!=CloudArray[iphi][ieta].end(); ++ic)
00480 output.push_back(*ic);
00481 }
00482 }
00483 }
00484
00485 delete theHitMatcher;
00486 edm::LogInfo("RoadSearch") << "Found " << output.size() << " clouds.";
00487 for ( RoadSearchCloudCollection::const_iterator ic = output.begin(); ic!=output.end(); ++ic)
00488 edm::LogInfo("RoadSearch") << " Cloud " << ic-output.begin()<< " has " << ic->size() << " hits.";
00489
00490 }
00491
00492 unsigned int RoadSearchCloudMakerAlgorithm::FillRecHitsIntoCloudGeneral(DetId id, double d0, double phi0, double k0, double phi1, double k1,
00493 Roads::type roadType, double ringPhi,
00494 const TrackerGeometry *tracker, const SiStripRecHitMatcher* theHitMatcher,
00495 RoadSearchCloud &cloud) {
00496
00497 unsigned int usedRecHits = 0;
00498
00499 bool double_ring_layer = !isSingleLayer(id);
00500
00501 std::vector<TrackingRecHit*> recHitVector = recHitVectorClass.getHitVector(&id);
00502
00503 for ( std::vector<TrackingRecHit*>::const_iterator recHitIterator = recHitVector.begin(); recHitIterator != recHitVector.end(); ++recHitIterator) {
00504
00505 if ( (unsigned int)id.subdetId() == StripSubdetector::TIB
00506 || (unsigned int)id.subdetId() == StripSubdetector::TOB
00507 || (unsigned int)id.subdetId() == StripSubdetector::TID
00508 || (unsigned int)id.subdetId() == StripSubdetector::TEC ) {
00509
00510 const SiStripRecHit2D *recHit = (SiStripRecHit2D*)(*recHitIterator);
00511 DetId hitId = recHit->geographicalId();
00512
00513 LogDebug("RoadSearch") << " Testing hit at (x/y/z): "
00514 << tracker->idToDet(recHit->geographicalId())->surface().toGlobal(recHit->localPosition()).x() << " / "
00515 << tracker->idToDet(recHit->geographicalId())->surface().toGlobal(recHit->localPosition()).y() << " / "
00516 << tracker->idToDet(recHit->geographicalId())->surface().toGlobal(recHit->localPosition()).z();
00517
00518 if ( roadType == Roads::RPhi ) {
00519 if (double_ring_layer && isSingleLayer(hitId)) {
00520
00521
00522
00523
00524
00525
00526 const GluedGeomDet *theGluedDet = dynamic_cast<const GluedGeomDet*>(tracker->idToDet(hitId));
00527
00528 SiStripMatchedRecHit2D* theCorrectedHit = CorrectMatchedHit(*recHitIterator,theGluedDet,
00529 tracker, theHitMatcher,
00530 k0, phi0);
00531 if (theCorrectedHit != 0){
00532
00533 GlobalPoint ghit = tracker->idToDet(theCorrectedHit->geographicalId())->surface().toGlobal(theCorrectedHit->localPosition());
00534 double hitRadius = sqrt(ghit.x()*ghit.x()+ghit.y()*ghit.y());
00535 double hitphi = map_phi(ghit.phi());
00536 double phi = phiFromExtrapolation(d0,phi0,k0,hitRadius,roadType);
00537
00538 float dp = (hitphi-phi);
00539 float dx = hitRadius*tan(dp);
00540
00541 LogDebug("RoadSearch") << " Hit phi = " << hitphi << " expected phi = " << phi
00542 <<" dx = " << dx << " for dxMax = " << phiMax(roadType,phi0,k0);
00543
00544
00545 if ( std::abs(dx) < phiMax(roadType,phi0,k0) ) {
00546 if ((usedRecHits < maxDetHitsInCloudPerDetId) && (cloud.size() < maxRecHitsInCloud_)) {
00547 cloud.addHit(recHit);
00548 ++usedRecHits;
00549 }
00550 }
00551 delete theCorrectedHit;
00552 }
00553 } else {
00554 if ( isBarrelSensor(hitId) ) {
00555
00556
00557
00558 GlobalPoint ghit = tracker->idToDet(recHit->geographicalId())->surface().toGlobal(recHit->localPosition());
00559 double hitRadius = sqrt(ghit.x()*ghit.x()+ghit.y()*ghit.y());
00560 double hitphi = map_phi(ghit.phi());
00561 double phi = phiFromExtrapolation(d0,phi0,k0,hitRadius,roadType);
00562
00563 float dp = (hitphi-phi);
00564 float dx = hitRadius*tan(dp);
00565 LogDebug("RoadSearch") << " Hit phi = " << hitphi << " expected phi = " << phi
00566 <<" dx = " << dx << " for dxMax = " << phiMax(roadType,phi0,k0);
00567
00568 if ( std::abs(dx) < phiMax(roadType,phi0,k0) ) {
00569 if ((usedRecHits < maxDetHitsInCloudPerDetId) && (cloud.size() < maxRecHitsInCloud_)) {
00570 cloud.addHit(recHit);
00571 ++usedRecHits;
00572 }
00573 }
00574 }
00575 else {
00576
00577 LocalPoint hit = recHit->localPosition();
00578 const StripTopology *topology = dynamic_cast<const StripTopology*>(&(tracker->idToDetUnit(hitId)->topology()));
00579 double stripAngle = topology->stripAngle(topology->strip(hit));
00580 double stripLength = topology->localStripLength(hit);
00581
00582 LocalPoint innerHitLocal(hit.x()+stripLength/2*std::sin(stripAngle),hit.y()-stripLength/2*std::cos(stripAngle),0);
00583 LocalPoint outerHitLocal(hit.x()-stripLength/2*std::sin(stripAngle),hit.y()+stripLength/2*std::cos(stripAngle),0);
00584
00585 double innerRadius = tracker->idToDetUnit(hitId)->surface().toGlobal(innerHitLocal).perp();
00586 double outerRadius = tracker->idToDetUnit(hitId)->surface().toGlobal(outerHitLocal).perp();
00587 double innerExtrapolatedPhi = phiFromExtrapolation(d0,phi0,k0,innerRadius,roadType);
00588 double outerExtrapolatedPhi = phiFromExtrapolation(d0,phi0,k0,outerRadius,roadType);
00589
00590 GlobalPoint innerHitGlobal =tracker->idToDetUnit(hitId)->surface().toGlobal(innerHitLocal);
00591 GlobalPoint outerHitGlobal =tracker->idToDetUnit(hitId)->surface().toGlobal(outerHitLocal);
00592
00593 GlobalPoint innerRoadGlobal(GlobalPoint::Cylindrical(innerRadius,innerExtrapolatedPhi,
00594 tracker->idToDetUnit(hitId)->surface().toGlobal(hit).z()));
00595 GlobalPoint outerRoadGlobal(GlobalPoint::Cylindrical(outerRadius,outerExtrapolatedPhi,
00596 tracker->idToDetUnit(hitId)->surface().toGlobal(hit).z()));
00597
00598 LocalPoint innerRoadLocal = tracker->idToDetUnit(hitId)->surface().toLocal(innerRoadGlobal);
00599 LocalPoint outerRoadLocal = tracker->idToDetUnit(hitId)->surface().toLocal(outerRoadGlobal);
00600
00601 double dxinter = CheckXYIntersection(innerHitLocal, outerHitLocal,
00602 innerRoadLocal, outerRoadLocal);
00603
00604 LogDebug("RoadSearch") << " Hit phi inner = " << innerHitGlobal.phi() << " and outer = " << outerHitGlobal.phi()
00605 << " expected inner phi = " << innerExtrapolatedPhi
00606 << " and outer phi = " << outerExtrapolatedPhi
00607 <<" dx = " << dxinter << " for dxMax = " << phiMax(roadType,phi0,k0);
00608
00609 if ( fabs(dxinter) < phiMax(roadType,phi0,k0)) {
00610
00611
00612
00613 if ((usedRecHits < maxDetHitsInCloudPerDetId) && (cloud.size() < maxRecHitsInCloud_)) {
00614 cloud.addHit(recHit);
00615 ++usedRecHits;
00616 }
00617 }
00618
00619
00620 }
00621 }
00622 } else {
00623
00624
00625
00626 if (double_ring_layer && isSingleLayer(hitId)) {
00627
00628
00629
00630
00631 const GluedGeomDet *theGluedDet = dynamic_cast<const GluedGeomDet*>(tracker->idToDet(hitId));
00632
00633 SiStripMatchedRecHit2D* theCorrectedHit = CorrectMatchedHit(*recHitIterator,theGluedDet,
00634 tracker, theHitMatcher,
00635 k1, phi1);
00636 if (theCorrectedHit != 0){
00637
00638 GlobalPoint ghit = tracker->idToDet(theCorrectedHit->geographicalId())->surface().toGlobal(theCorrectedHit->localPosition());
00639 double hitphi = map_phi(ghit.phi());
00640 double hitZ = ghit.z();
00641 double phi = phiFromExtrapolation(d0,phi0,k0,hitZ,roadType);
00642
00643 float dp = hitphi-phi;
00644 float dx = hitZ*tan(dp);
00645
00646
00647
00648
00649 if ( std::abs(dx) < phiMax(roadType,phi0,k1)) {
00650 if ((usedRecHits < maxDetHitsInCloudPerDetId) && (cloud.size() < maxRecHitsInCloud_)) {
00651 cloud.addHit(recHit);
00652 ++usedRecHits;
00653 }
00654 }
00655 delete theCorrectedHit;
00656 }
00657 } else {
00658 if ( isBarrelSensor(hitId) ) {
00659
00660
00661
00662 LocalPoint hit = recHit->localPosition();
00663 const StripTopology *topology = dynamic_cast<const StripTopology*>(&(tracker->idToDetUnit(hitId)->topology()));
00664 double stripAngle = topology->stripAngle(topology->strip(hit));
00665 double stripLength = topology->localStripLength(hit);
00666
00667
00668
00669 LocalPoint innerHitLocal(hit.x()+stripLength/2*std::sin(stripAngle),hit.y()-stripLength/2*std::cos(stripAngle),0);
00670 LocalPoint outerHitLocal(hit.x()-stripLength/2*std::sin(stripAngle),hit.y()+stripLength/2*std::cos(stripAngle),0);
00671 double innerHitPhi = map_phi(tracker->idToDetUnit(hitId)->surface().toGlobal(innerHitLocal).phi());
00672 double outerHitPhi = map_phi(tracker->idToDetUnit(hitId)->surface().toGlobal(outerHitLocal).phi());
00673 double innerHitZ = tracker->idToDetUnit(hitId)->surface().toGlobal(innerHitLocal).z();
00674 double outerHitZ = tracker->idToDetUnit(hitId)->surface().toGlobal(outerHitLocal).z();
00675 double innerExtrapolatedPhi = phiFromExtrapolation(d0,phi0,k0,innerHitZ,roadType);
00676 double outerExtrapolatedPhi = phiFromExtrapolation(d0,phi0,k0,outerHitZ,roadType);
00677
00678 double midPointZ = 0.5*(innerHitZ+outerHitZ);
00679
00680 double dPhiInter = CheckZPhiIntersection(innerHitPhi, innerHitZ, outerHitPhi, outerHitZ,
00681 innerExtrapolatedPhi, innerHitZ,
00682 outerExtrapolatedPhi, outerHitZ);
00683
00684 double dX = midPointZ*tan(dPhiInter);
00685
00686 if (std::abs(dX) < 1.5*phiMax(roadType,phi0,k1)) {
00687 if ((usedRecHits < maxDetHitsInCloudPerDetId) && (cloud.size() < maxRecHitsInCloud_)) {
00688 cloud.addHit(recHit);
00689 ++usedRecHits;
00690 }
00691 }
00692
00693 } else {
00694
00695
00696
00697
00698 LocalPoint hit = recHit->localPosition();
00699 const StripTopology *topology = dynamic_cast<const StripTopology*>(&(tracker->idToDetUnit(hitId)->topology()));
00700 double stripAngle = topology->stripAngle(topology->strip(hit));
00701 double stripLength = topology->localStripLength(hit);
00702
00703 double hitZ = tracker->idToDetUnit(hitId)->surface().toGlobal(hit).z();
00704 double extrapolatedPhi = phiFromExtrapolation(d0,phi0,k0,hitZ,roadType);
00705
00706 LocalPoint innerHitLocal(hit.x()+stripLength/2*std::sin(stripAngle),hit.y()-stripLength/2*std::cos(stripAngle),0);
00707 LocalPoint outerHitLocal(hit.x()-stripLength/2*std::sin(stripAngle),hit.y()+stripLength/2*std::cos(stripAngle),0);
00708
00709 double innerHitPhi = map_phi(tracker->idToDetUnit(hitId)->surface().toGlobal(innerHitLocal).phi());
00710 double outerHitPhi = map_phi(tracker->idToDetUnit(hitId)->surface().toGlobal(outerHitLocal).phi());
00711
00712
00713
00714
00715 double deltaPhi = ZPhiDeltaPhi(innerHitPhi,outerHitPhi,extrapolatedPhi);
00716 double deltaX = hitZ*tan(deltaPhi);
00717 if (std::abs(deltaX) < phiMax(roadType,phi0,k1)){
00718 if ((usedRecHits < maxDetHitsInCloudPerDetId) && (cloud.size() < maxRecHitsInCloud_)) {
00719 cloud.addHit(recHit);
00720 ++usedRecHits;
00721 }
00722 }
00723 }
00724 }
00725 }
00726 } else if ( (unsigned int)id.subdetId() == PixelSubdetector::PixelBarrel
00727 || (unsigned int)id.subdetId() == PixelSubdetector::PixelEndcap) {
00728 if ( UsePixels ) {
00729
00730 const SiPixelRecHit *recHit = (SiPixelRecHit*)(*recHitIterator);
00731
00732 if ( roadType == Roads::RPhi ) {
00733
00734 if ( isBarrelSensor(id) ) {
00735
00736
00737 GlobalPoint ghit = tracker->idToDet(recHit->geographicalId())->surface().toGlobal(recHit->localPosition());
00738 double hitRadius = sqrt(ghit.x()*ghit.x()+ghit.y()*ghit.y());
00739 double hitphi = map_phi(ghit.phi());
00740 double phi = phiFromExtrapolation(d0,phi0,k0,hitRadius,roadType);
00741
00742 float dp = hitphi-phi;
00743 float dx = hitRadius*tan(dp);
00744
00745
00746 if ( std::abs(dx) < phiMax(roadType,phi0,k0) ) {
00747 cloud.addHit(recHit);
00748 ++usedRecHits;
00749 }
00750 } else {
00751
00752
00753
00754
00755 LocalPoint hit = recHit->localPosition();
00756
00757
00758 double hitphi = map_phi(tracker->idToDetUnit(id)->surface().toGlobal(hit).phi());
00759
00760
00761 GlobalPoint ghit = tracker->idToDet(recHit->geographicalId())->surface().toGlobal(recHit->localPosition());
00762
00763
00764 double hitRadius = sqrt(ghit.x()*ghit.x()+ghit.y()*ghit.y());
00765
00766
00767 double phi = phiFromExtrapolation(d0,phi0,k0,hitRadius,roadType);
00768
00769 if ( std::abs(hitphi-phi) < phiMax(roadType,phi0,k0) ) {
00770 cloud.addHit(recHit);
00771 ++usedRecHits;
00772 }
00773 }
00774 } else {
00775
00776 GlobalPoint ghit = tracker->idToDet(recHit->geographicalId())->surface().toGlobal(recHit->localPosition());
00777 double phi = phiFromExtrapolation(d0,phi0,k0,ghit.z(),roadType);
00778 double hitphi = map_phi(ghit.phi());
00779 double dphi = map_phi2(hitphi-phi);
00780 float dx = ghit.z()*tan(dphi);
00781
00782 if ( std::abs(dx) < 0.25 ) {
00783 cloud.addHit(recHit);
00784 ++usedRecHits;
00785 }
00786 }
00787 }
00788 } else {
00789 edm::LogError("RoadSearch") << "recHitVector from general hit access function contains unknown detector id: " << (unsigned int)id.subdetId() << " rawId: " << id.rawId();
00790 }
00791
00792 }
00793
00794
00795 return usedRecHits;
00796 }
00797
00798 unsigned int RoadSearchCloudMakerAlgorithm::FillPixRecHitsIntoCloud(DetId id, const SiPixelRecHitCollection *inputRecHits,
00799 double d0, double phi0, double k0, Roads::type roadType, double ringPhi,
00800 const TrackerGeometry *tracker, RoadSearchCloud &cloud) {
00801
00802
00803 unsigned int usedRecHits = 0;
00804
00805
00806
00807
00808
00809
00810
00811
00812
00813 SiPixelRecHitCollection::const_iterator recHitMatch = inputRecHits->find(id);
00814 if (recHitMatch == inputRecHits->end()) return usedRecHits;
00815
00816 const SiPixelRecHitCollection::DetSet recHitRange = *recHitMatch;
00817
00818 for ( SiPixelRecHitCollection::DetSet::const_iterator recHitIterator = recHitRange.begin();
00819 recHitIterator != recHitRange.end(); ++recHitIterator) {
00820
00821 const SiPixelRecHit * recHit = &(*recHitIterator);
00822
00823 if ( roadType == Roads::RPhi ) {
00824
00825 if ( isBarrelSensor(id) ) {
00826
00827
00828 GlobalPoint ghit = tracker->idToDet(recHit->geographicalId())->surface().toGlobal(recHit->localPosition());
00829 double hitRadius = sqrt(ghit.x()*ghit.x()+ghit.y()*ghit.y());
00830 double hitphi = map_phi(ghit.phi());
00831 double phi = phiFromExtrapolation(d0,phi0,k0,hitRadius,roadType);
00832
00833 if ( std::abs(hitphi-phi) < phiMax(roadType,phi0,k0) ) {
00834 cloud.addHit(recHit);
00835 ++usedRecHits;
00836 }
00837 }
00838 else {
00839
00840
00841
00842
00843 LocalPoint hit = recHit->localPosition();
00844
00845
00846 double hitphi = map_phi(tracker->idToDetUnit(id)->surface().toGlobal(hit).phi());
00847
00848
00849 GlobalPoint ghit = tracker->idToDet(recHit->geographicalId())->surface().toGlobal(recHit->localPosition());
00850
00851
00852 double hitRadius = sqrt(ghit.x()*ghit.x()+ghit.y()*ghit.y());
00853
00854
00855 double phi = phiFromExtrapolation(d0,phi0,k0,hitRadius,roadType);
00856
00857 if ( std::abs(hitphi-phi) < phiMax(roadType,phi0,k0) ) {
00858 cloud.addHit(recHit);
00859 ++usedRecHits;
00860 }
00861 }
00862 }
00863
00864 else {
00865
00866 GlobalPoint ghit = tracker->idToDet(recHit->geographicalId())->surface().toGlobal(recHit->localPosition());
00867
00868 double phi = phiFromExtrapolation(d0,phi0,k0,ghit.z(),roadType);
00869 if ( (phi - phiMax(roadType,phi0,k0)) < ringPhi && (phi + phiMax(roadType,phi0,k0))>ringPhi ) {
00870 cloud.addHit(recHit);
00871 ++usedRecHits;
00872 }
00873 }
00874
00875 }
00876
00877 return usedRecHits;
00878 }
00879
00880 bool RoadSearchCloudMakerAlgorithm::isSingleLayer(DetId id) {
00881
00882 if ( (unsigned int)id.subdetId() == StripSubdetector::TIB ) {
00883 TIBDetId tibid(id.rawId());
00884 if ( !tibid.glued() ) {
00885 return true;
00886 }
00887 } else if ( (unsigned int)id.subdetId() == StripSubdetector::TOB ) {
00888 TOBDetId tobid(id.rawId());
00889 if ( !tobid.glued() ) {
00890 return true;
00891 }
00892 } else if ( (unsigned int)id.subdetId() == StripSubdetector::TID ) {
00893 TIDDetId tidid(id.rawId());
00894 if ( !tidid.glued() ) {
00895 return true;
00896 }
00897 } else if ( (unsigned int)id.subdetId() == StripSubdetector::TEC ) {
00898 TECDetId tecid(id.rawId());
00899 if ( !tecid.glued() ) {
00900 return true;
00901 }
00902 } else {
00903 return false;
00904 }
00905
00906 return false;
00907 }
00908
00909 bool RoadSearchCloudMakerAlgorithm::isBarrelSensor(DetId id) {
00910
00911 if ( (unsigned int)id.subdetId() == StripSubdetector::TIB ) {
00912 return true;
00913 } else if ( (unsigned int)id.subdetId() == StripSubdetector::TOB ) {
00914 return true;
00915 } else if ( (unsigned int)id.subdetId() == PixelSubdetector::PixelBarrel ) {
00916 return true;
00917 } else {
00918 return false;
00919 }
00920
00921 }
00922
00923 double RoadSearchCloudMakerAlgorithm::phiFromExtrapolation(double d0, double phi0, double k0, double ringRadius, Roads::type roadType) {
00924
00925 double ringPhi = -99.;
00926 if ( roadType == Roads::RPhi ) {
00927 double omega=k0, rl=ringRadius;
00928 double sp0=sin(phi0); double cp0=cos(phi0);
00929 if (fabs(omega)>0.000005){
00930 double xc=-sp0*(d0+1.0/omega);
00931 double yc=cp0*(d0+1.0/omega);
00932 double rh=fabs(1.0/omega);
00933 double bbb=fabs(d0+1.0/omega);
00934 double sss=0.5*(rl+rh+bbb);
00935 double ddd=sqrt((sss-bbb)*(sss-rh)/(sss*(sss-rl)));
00936 double phil1=2.0*atan(ddd);
00937 double phit=phi0+phil1; if (omega<0.0)phit=phi0-phil1;
00938 double xh=xc+sin(phit)/omega;
00939 double yh=yc-cos(phit)/omega;
00940 double phih=atan2(yh,xh);
00941 ringPhi = map_phi(phih);
00942 }
00943 else {
00944 double cee = rl*rl - d0*d0 -0.25*omega*omega - omega*d0;
00945 if (cee<0.0){return ringPhi;}
00946 double l = sqrt(cee);
00947 double xh=-sp0*d0+l*cp0-0.5*l*l*omega*sp0;
00948 double yh= cp0*d0+l*sp0+0.5*l*l*omega*cp0;
00949 double phih=atan2(yh,xh);
00950 ringPhi = map_phi(phih);
00951 }
00952 }
00953 else {
00954 ringPhi = map_phi(phi0 + k0 * ringRadius);
00955 }
00956
00957 return ringPhi;
00958 }
00959
00960 double RoadSearchCloudMakerAlgorithm::phiMax(Roads::type roadType,
00961 double phi0, double k0) {
00962
00963 double dphi;
00964 if ( roadType == Roads::RPhi ) {
00965
00966
00967 dphi = theRPhiRoadSize + 0.15*82.0*fabs(k0);
00968 }
00969 else if ( roadType == Roads::ZPhi ) {
00970 dphi = theZPhiRoadSize + 0.4*82.0*fabs(k0);
00971 }
00972 else {
00973 edm::LogWarning("RoadSearch") << "Bad roadType: "<< roadType;
00974 dphi = theZPhiRoadSize;
00975 }
00976 return dphi;
00977
00978 }
00979
00980 void RoadSearchCloudMakerAlgorithm::makecircle(double x1, double y1,
00981 double x2,double y2, double x3, double y3){
00982 double x1t=x1-x3; double y1t=y1-y3; double r1s=x1t*x1t+y1t*y1t;
00983 double x2t=x2-x3; double y2t=y2-y3; double r2s=x2t*x2t+y2t*y2t;
00984 double rho=x1t*y2t-x2t*y1t;
00985 double xc, yc, rc, fac;
00986 if (fabs(rho)<RoadSearchCloudMakerAlgorithm::epsilon){
00987 rc=1.0/(RoadSearchCloudMakerAlgorithm::epsilon);
00988 fac=sqrt(x1t*x1t+y1t*y1t);
00989 xc=x2+y1t*rc/fac;
00990 yc=y2-x1t*rc/fac;
00991 }else{
00992 fac=0.5/rho;
00993 xc=fac*(r1s*y2t-r2s*y1t);
00994 yc=fac*(r2s*x1t-r1s*x2t);
00995 rc=sqrt(xc*xc+yc*yc); xc+=x3; yc+=y3;
00996 }
00997 double s3=0.0;
00998 double f1=x1*yc-y1*xc; double f2=x2*yc-y2*xc;
00999 double f3=x3*yc-y3*xc;
01000 if ((f1<0.0)&&(f2<0.0)&&(f3<=0.0))s3=1.0;
01001 if ((f1>0.0)&&(f2>0.0)&&(f3>=0.0))s3=-1.0;
01002 d0h=-s3*(sqrt(xc*xc+yc*yc)-rc);
01003 phi0h=atan2(yc,xc)+s3*Geom::halfPi();
01004 omegah=-s3/rc;
01005 }
01006
01007 double RoadSearchCloudMakerAlgorithm::CheckXYIntersection(LocalPoint& inner1, LocalPoint& outer1,
01008 LocalPoint& inner2, LocalPoint& outer2){
01009
01010 double deltaX = -999.;
01011
01012
01013 double det12 = inner1.x()*outer1.y() - inner1.y()*outer1.x();
01014 double det34 = inner2.x()*outer2.y() - inner2.y()*outer2.x();
01015
01016 double xinter = (det12*(inner2.x()-outer2.x()) - det34*(inner1.x()-outer1.x()))/
01017 ((inner1.x()-outer1.x())*(inner2.y()-outer2.y()) -
01018 (inner2.x()-outer2.x())*(inner1.y()-outer1.y()));
01019
01020 bool inter = true;
01021 if (inner1.x() < outer1.x()){
01022 if ((xinter<inner1.x()) || (xinter>outer1.x())) inter = false;
01023 }
01024 else{
01025 if ((xinter>inner1.x()) || (xinter<outer1.x())) inter = false;
01026 }
01027
01028 if (inner2.x() < outer2.x()){
01029 if ((xinter<inner2.x()) || (xinter>outer2.x())) inter = false;
01030 }
01031 else{
01032 if ((xinter>inner2.x()) || (xinter<outer2.x())) inter = false;
01033 }
01034
01035 if (inter){
01036 deltaX = 0;
01037 }
01038 else{
01039 deltaX = min(fabs(inner1.x()-inner2.x()),fabs(outer1.x()-outer2.x()));
01040 }
01041 return deltaX;
01042
01043 }
01044
01045 double RoadSearchCloudMakerAlgorithm::CheckZPhiIntersection(double iPhi1, double iZ1, double oPhi1, double oZ1,
01046 double iPhi2, double iZ2, double oPhi2, double oZ2){
01047
01048
01049 if ((iPhi1 > Geom::pi() || oPhi1 > Geom::pi() || iPhi2 > Geom::pi() || oPhi2 > Geom::pi()) &&
01050 (iPhi1 < Geom::pi() || oPhi1 < Geom::pi() || iPhi2 < Geom::pi() || oPhi2 < Geom::pi())){
01051 iPhi1 = map_phi2(iPhi1); oPhi1 = map_phi2(oPhi1);
01052 iPhi2 = map_phi2(iPhi2); oPhi2 = map_phi2(oPhi2);
01053 }
01054
01055 double deltaPhi = -999.;
01056
01057
01058 double det12 = iZ1*oPhi1 - iPhi1*oZ1;
01059 double det34 = iZ2*oPhi2 - iPhi2*oZ2;
01060
01061 double xinter = (det12*(iZ2-oZ2) - det34*(iZ1-oZ1))/
01062 ((iZ1-oZ1)*(iPhi2-oPhi2) -
01063 (iZ2-oZ2)*(iPhi1-oPhi1));
01064
01065 bool inter = true;
01066 if (iZ1 < oZ1){
01067 if ((xinter<iZ1) || (xinter>oZ1)) inter = false;
01068 }
01069 else{
01070 if ((xinter>iZ1) || (xinter<oZ1)) inter = false;
01071 }
01072
01073 if (iZ2 < oZ2){
01074 if ((xinter<iZ2) || (xinter>oZ2)) inter = false;
01075 }
01076 else{
01077 if ((xinter>iZ2) || (xinter<oZ2)) inter = false;
01078 }
01079
01080 if (inter){
01081 deltaPhi = 0;
01082 }
01083 else{
01084 deltaPhi = min(fabs(iPhi2-iPhi1),fabs(oPhi2-oPhi1));
01085 }
01086 return deltaPhi;
01087
01088 }
01089
01090
01091 double RoadSearchCloudMakerAlgorithm::ZPhiDeltaPhi(double hitPhi1, double hitPhi2, double predictedPhi){
01092
01093 double deltaPhi = -999.;
01094
01095 double dPhiHits = map_phi2(hitPhi1-hitPhi2);
01096 double dPhi1 = map_phi2(hitPhi1-predictedPhi);
01097 double dPhi2 = map_phi2(hitPhi2-predictedPhi);
01098
01099 if (dPhiHits >= 0){
01100 if ( (dPhi1>=0.0) && (dPhi2 <= 0.0))
01101 deltaPhi = 0.0;
01102 else{
01103 if (std::abs(dPhi1)<std::abs(dPhi2))
01104 deltaPhi = dPhi1;
01105 else
01106 deltaPhi = dPhi2;
01107 }
01108 }
01109 else {
01110 if ( (dPhi1<=0.0) && (dPhi2 >= 0.0))
01111 deltaPhi = 0.0;
01112 else{
01113 if (std::abs(dPhi1)<std::abs(dPhi2))
01114 deltaPhi = dPhi1;
01115 else
01116 deltaPhi = dPhi2;
01117 }
01118 }
01119
01120 return deltaPhi;
01121
01122 }
01123
01124 RoadSearchCloudCollection RoadSearchCloudMakerAlgorithm::Clean(RoadSearchCloudCollection* inputCollection){
01125
01126 RoadSearchCloudCollection output;
01127
01128
01129
01130
01131
01132 if ( inputCollection->empty() ){
01133 LogDebug("RoadSearch") << "Found " << output.size() << " clean clouds.";
01134 return output;
01135 }
01136
01137
01138
01139
01140
01141 if ( 1==inputCollection->size() ){
01142 output = *inputCollection;
01143
01144
01145
01146 LogDebug("RoadSearch") << "Found " << output.size() << " clean clouds.";
01147 return output;
01148 }
01149
01150
01151
01152
01153 std::vector<bool> already_gone(inputCollection->size());
01154 for (unsigned int i=0; i<inputCollection->size(); ++i) {
01155 already_gone[i] = false;
01156 }
01157
01158 int raw_cloud_ctr=0;
01159
01160 for ( RoadSearchCloudCollection::const_iterator raw_cloud = inputCollection->begin(); raw_cloud != inputCollection->end(); ++raw_cloud) {
01161 ++raw_cloud_ctr;
01162
01163 if (already_gone[raw_cloud_ctr-1])continue;
01164
01165
01166
01167
01168
01169 RoadSearchCloud lone_cloud = *raw_cloud;
01170
01171 int second_cloud_ctr=raw_cloud_ctr;
01172 for ( RoadSearchCloudCollection::const_iterator second_cloud = raw_cloud+1; second_cloud != inputCollection->end(); ++second_cloud) {
01173 second_cloud_ctr++;
01174
01175 std::vector<const TrackingRecHit*> unshared_hits;
01176
01177 if ( already_gone[second_cloud_ctr-1] )continue;
01178
01179 for ( RoadSearchCloud::RecHitVector::const_iterator second_cloud_hit = second_cloud->begin_hits();
01180 second_cloud_hit != second_cloud->end_hits();
01181 ++ second_cloud_hit ) {
01182 bool is_shared = false;
01183 for ( RoadSearchCloud::RecHitVector::const_iterator lone_cloud_hit = lone_cloud.begin_hits();
01184 lone_cloud_hit != lone_cloud.end_hits();
01185 ++ lone_cloud_hit ) {
01186
01187 if ((*lone_cloud_hit)->geographicalId() == (*second_cloud_hit)->geographicalId())
01188 if ((*lone_cloud_hit)->localPosition().x() == (*second_cloud_hit)->localPosition().x())
01189 if ((*lone_cloud_hit)->localPosition().y() == (*second_cloud_hit)->localPosition().y())
01190 {is_shared=true; break;}
01191 }
01192 if (!is_shared) unshared_hits.push_back(*second_cloud_hit);
01193
01194 if ( ((float(unshared_hits.size())/float(lone_cloud.size())) >
01195 ((float(second_cloud->size())/float(lone_cloud.size()))-mergingFraction_)) &&
01196 ((float(unshared_hits.size())/float(second_cloud->size())) > (1-mergingFraction_))){
01197
01198 break;
01199 }
01200
01201 if (lone_cloud.size()+unshared_hits.size() > maxRecHitsInCloud_) {
01202 break;
01203 }
01204
01205 }
01206
01207 double f_lone_shared=double(second_cloud->size()-unshared_hits.size())/double(lone_cloud.size());
01208 double f_second_shared=double(second_cloud->size()-unshared_hits.size())/double(second_cloud->size());
01209
01210 if ( ( (static_cast<unsigned int>(f_lone_shared*1E9) > static_cast<unsigned int>(mergingFraction_*1E9))||(static_cast<unsigned int>(f_second_shared*1E9) > static_cast<unsigned int>(mergingFraction_*1E9)) )
01211 && (lone_cloud.size()+unshared_hits.size() <= maxRecHitsInCloud_) ){
01212
01213 LogDebug("RoadSearch") << " Merge CloudA: " << raw_cloud_ctr << " with CloudB: " << second_cloud_ctr
01214 << " Shared fractions are " << f_lone_shared << " and " << f_second_shared;
01215
01216
01217
01218
01219 for (unsigned int k=0; k<unshared_hits.size(); ++k) {
01220 lone_cloud.addHit(unshared_hits[k]);
01221 }
01222
01223 already_gone[second_cloud_ctr-1]=true;
01224
01225 }
01226
01227 }
01228
01229 output.push_back(lone_cloud);
01230
01231 }
01232
01233 LogDebug("RoadSearch") << "Found " << output.size() << " clean clouds.";
01234
01235 return output;
01236 }
01237
01238 SiStripMatchedRecHit2D* RoadSearchCloudMakerAlgorithm::CorrectMatchedHit(const TrackingRecHit *originalHit,
01239 const GluedGeomDet* gluedDet,
01240 const TrackerGeometry *tracker,
01241 const SiStripRecHitMatcher* theHitMatcher,
01242 double k0, double phi0) {
01243
01244
01245
01246 const SiStripMatchedRecHit2D *theRH = dynamic_cast<const SiStripMatchedRecHit2D*>(originalHit);
01247 if (theRH == 0) {
01248 std::cout<<" Could not cast original hit" << std::endl;
01249 }
01250 if (theRH != 0){
01251 const GeomDet *recHitGeomDet = tracker->idToDet(theRH->geographicalId());
01252 const GluedGeomDet *theGluedDet = dynamic_cast<const GluedGeomDet*>(recHitGeomDet);
01253
01254 const GeomDetUnit* theMonoDet = theGluedDet->monoDet();
01255 const SiStripRecHit2D theMonoHit = theRH->monoHit();
01256
01257
01258 GlobalPoint gcenterofstrip=(theMonoDet->surface()).toGlobal(theMonoHit.localPosition());
01259
01260 float gtrackangle_xy = map_phi2(phi0 + 2.0*asin(0.5*gcenterofstrip.perp()*k0));
01261 float rzangle = atan2(gcenterofstrip.perp(),gcenterofstrip.z());
01262
01263 GlobalVector gtrackangle2(cos(gtrackangle_xy)*sin(rzangle),
01264 sin(gtrackangle_xy)*sin(rzangle),
01265 cos(rzangle));
01266 LocalVector trackdirection2=((tracker->idToDet(theRH->geographicalId()))->surface()).toLocal(gtrackangle2);
01267
01268
01269 SiStripMatchedRecHit2D* theCorrectedHit = theHitMatcher->match(theRH,theGluedDet,trackdirection2);
01270 if (theCorrectedHit!=0) return theCorrectedHit;
01271 }
01272
01273 return 0;
01274 }