CMS 3D CMS Logo

 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Pages
PhiBorderFinder.h
Go to the documentation of this file.
1 #ifndef PhiBorderFinder_H
2 #define PhiBorderFinder_H
3 
13 
16 
21 
22 // FIXME: remove this include
24 
25 #include <vector>
26 
28 public:
29 
30  typedef DetRod Det; //FIXME!!!
32 
33 
34  PhiBorderFinder(const std::vector<const Det*>& utheDets)
36  std::vector<const Det*> theDets = utheDets;
37  precomputed_value_sort(theDets.begin(), theDets.end(), DetPhi());
38 
39  const std::string metname = "Muon|RecoMuon|RecoMuonDetLayers|PhiBorderFinder";
40 
41  double step = 2.*Geom::pi()/theNbins;
42 
43  LogTrace(metname) << "RecoMuonDetLayers::PhiBorderFinder "
44  << "step w: " << step << " # of bins: " << theNbins;
45 
46  std::vector<double> spread(theNbins);
47  std::vector<std::pair<double,double> > phiEdge;
48  phiEdge.reserve(theNbins);
49  thePhiBorders.reserve(theNbins);
50  thePhiBins.reserve(theNbins);
51  for ( unsigned int i = 0; i < theNbins; i++ ) {
52  thePhiBins.push_back(theDets[i]->position().phi());
53  spread.push_back(theDets[i]->position().phi()
54  - (theDets[0]->position().phi() + i*step));
55 
56  LogTrace(metname) << "bin: " << i << " phi bin: " << thePhiBins[i]
57  << " spread: " << spread[i];
58 
59 
61  dynamic_cast<const BoundPlane*>(&theDets[i]->surface());
62  if (plane==0) {
63  //FIXME
64  throw cms::Exception("UnexpectedState") << ("PhiBorderFinder: det surface is not a BoundPlane");
65  }
66 
67  std::vector<GlobalPoint> dc =
68  BoundingBox().corners(*plane);
69 
70  float phimin(999.), phimax(-999.);
71  for (std::vector<GlobalPoint>::const_iterator pt=dc.begin();
72  pt!=dc.end(); pt++) {
73  float phi = (*pt).phi();
74 // float z = pt->z();
75  if (phi < phimin) phimin = phi;
76  if (phi > phimax) phimax = phi;
77  }
78  if (phimin*phimax < 0. && //Handle pi border:
79  phimax - phimin > Geom::pi()) { //Assume that the Det is on
80  //the shortest side
81  std::swap(phimin,phimax);
82  }
83  phiEdge.push_back(std::pair<double,double>(phimin,phimax));
84  }
85 
86  for (unsigned int i = 0; i < theNbins; i++) {
87 
88  // Put the two phi values in the [0,2pi] range
89  double firstPhi = positiveRange(phiEdge[i].first);
90  double secondPhi = positiveRange(phiEdge[binIndex(i-1)].second);
91 
92  // Reformat them in the [-pi,pi] range
93  Geom::Phi<double> firstEdge(firstPhi);
94  Geom::Phi<double> secondEdge(secondPhi);
95 
96  // Calculate the mean and format the result in the [-pi,pi] range
97  // Get their value in order to perform the mean in the correct way
98  Geom::Phi<double> mean((firstEdge.value() + secondEdge.value())/2.);
99 
100  // Special case: at +-pi there is a discontinuity
101  if ( phiEdge[i].first * phiEdge[binIndex(i-1)].second < 0 &&
102  fabs(firstPhi-secondPhi) < Geom::pi() )
103  mean = Geom::pi() - mean;
104 
105  thePhiBorders.push_back(mean);
106  }
107 
108  for (unsigned int i = 0; i < theNbins; i++) {
109  if (Geom::Phi<double>(phiEdge[i].first)
110  - Geom::Phi<double>(phiEdge[binIndex(i-1)].second) < 0) {
111  isPhiOverlapping_ = true;
112  break;
113  }
114  }
115 
116  double rms = stat_RMS(spread);
117  if ( rms < 0.01*step) {
118  isPhiPeriodic_ = true;
119  }
120 
121  //Check that everything is proper
122  if (thePhiBorders.size() != theNbins || thePhiBins.size() != theNbins)
123  //FIXME
124  throw cms::Exception("UnexpectedState") << "PhiBorderFinder: consistency error";
125  }
126 
127 
128  virtual ~PhiBorderFinder(){};
129 
130  inline unsigned int nBins() {return theNbins;}
131 
133  inline bool isPhiPeriodic() const { return isPhiPeriodic_; }
134 
136  inline bool isPhiOverlapping() const { return isPhiOverlapping_; }
137 
140  inline const std::vector<double>& phiBorders() const { return thePhiBorders; }
141 
143  inline const std::vector<double>& phiBins() const { return thePhiBins; }
144 
145  // inline std::vector<double> etaBorders() {}
146  // inline std::vector<double> zBorders() {}
147 
148 private:
149  unsigned int theNbins;
152  std::vector<double> thePhiBorders;
153  std::vector<double> thePhiBins;
154 
155  inline double positiveRange (double phi) const
156  {
157  return (phi > 0) ? phi : phi + Geom::twoPi();
158  }
159 
160  int binIndex( int i) const {
161  int ind = i % (int)theNbins;
162  return (ind < 0) ? ind+theNbins : ind;
163  }
164 
165 
166 };
167 #endif
168 
int i
Definition: DBlmapReader.cc:9
const std::string metname
geomsort::ExtractPhi< Det, float > DetPhi
virtual ~PhiBorderFinder()
U second(std::pair< T, U > const &p)
const std::vector< double > & phiBorders() const
void swap(edm::DataFrameContainer &lhs, edm::DataFrameContainer &rhs)
std::vector< double > thePhiBorders
PhiBorderFinder(const std::vector< const Det * > &utheDets)
double stat_RMS(const CONT &cont)
Definition: simple_stat.h:20
#define LogTrace(id)
T value() const
Explicit access to value in case implicit conversion not OK.
Definition: Phi.h:38
bool isPhiPeriodic() const
Returns true if the Dets are periodic in phi.
Definition: DetRod.h:13
unsigned int nBins()
static std::vector< GlobalPoint > corners(const Plane &)
Definition: BoundingBox.cc:24
void precomputed_value_sort(RandomAccessIterator begin, RandomAccessIterator end, const Extractor &extr)
static int position[264][3]
Definition: ReadPGInfo.cc:509
double positiveRange(double phi) const
std::vector< double > thePhiBins
bool isPhiOverlapping() const
Returns true if any 2 of the Det overlap in phi.
volatile std::atomic< bool > shutdown_flag false
constexpr double pi()
Definition: Pi.h:31
constexpr double twoPi()
Definition: Pi.h:32
int binIndex(int i) const
tuple size
Write out results.
const std::vector< double > & phiBins() const
The centers of the Dets.
unsigned int theNbins