All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
PCA.cc
Go to the documentation of this file.
1 #include "PCA.h"
2 
3 using namespace sbnpca;
4 
5 float sbnpca::VecAngle(std::array<float, 2> A, std::array<float, 2> B) {
6  float costh = (A[0] * B[0] + A[1] * B[1]) \
7  / (sqrt(A[0]*A[0] + A[1] * A[1]) * sqrt(B[0]*B[0] + B[1] * B[1]));
8 
9  return acos(costh);
10 }
11 
12 std::array<float, 2> sbnpca::HitVector(const recob::Hit &A, const geo::GeometryCore *geo, const detinfo::DetectorPropertiesData &dprop) {
13  // get the wire distance between A and B
14  float wire_distance = A.WireID().Wire;
15  // convert to cm
16  float wire_distance_cm = wire_distance * geo->WirePitch();
17 
18  // and the time difference
19  float time_distance = A.PeakTime();
20  // convert to cm
21  float time_distance_cm = dprop.ConvertTicksToX(time_distance, A.WireID());
22 
23  return {wire_distance_cm, time_distance_cm};
24 }
25 
26 std::array<float, 2> sbnpca::HitVector(const recob::Hit &A, const recob::Hit &B, const geo::GeometryCore *geo, const detinfo::DetectorPropertiesData &dprop) {
27  // get each individual vec
28  std::array<float, 2> vecA = HitVector(A, geo, dprop);
29  std::array<float, 2> vecB = HitVector(B, geo, dprop);
30 
31  return {vecA[0] - vecB[0], vecA[1] - vecB[1]};
32 }
33 
35  std::array<float, 2> vec = HitVector(A, B, geo, dprop);
36  return sqrt(vec[0]*vec[0] + vec[1]*vec[1]);
37 }
38 
39 std::tuple<std::vector<art::Ptr<recob::Hit>>, std::vector<art::Ptr<recob::Hit>>, bool> sbnpca::GetNearestHits(
40  const std::vector<art::Ptr<recob::Hit>> &hits, int ihit, float distance,
41  const geo::GeometryCore *geo,
42  const detinfo::DetectorPropertiesData &dprop) {
43  std::vector<art::Ptr<recob::Hit>> retlo;
44  std::vector<art::Ptr<recob::Hit>> rethi;
45 
46  bool lo_complete = false;
47  // pull in smaller ones
48  for (int j = ihit-1; j >= 0; j--) {
49  if (HitDistance(*hits[j], *hits[ihit], geo, dprop) > distance) {
50  lo_complete = true;
51  break;
52  }
53  retlo.push_back(hits[j]);
54  }
55 
56  bool hi_complete = false;
57  // pull in larger ones
58  for (unsigned j = ihit+1; j < hits.size(); j++) {
59  if (HitDistance(*hits[j], *hits[ihit], geo, dprop) > distance) {
60  hi_complete = true;
61  break;
62  }
63  rethi.push_back(hits[j]);
64  }
65 
66  return {retlo, rethi, lo_complete && hi_complete};
67 }
68 
69 std::array<float, 2> sbnpca::HitPCAVec(const std::vector<art::Ptr<recob::Hit>> &hits, const recob::Hit &center,
70  const geo::GeometryCore *geo, const detinfo::DetectorPropertiesData &dprop) {
71 
72  return HitPCAVec(hits, HitVector(center, geo, dprop), geo, dprop);
73 }
74 
75 std::array<float, 2> sbnpca::HitPCAVec(const std::vector<art::Ptr<recob::Hit>> &hits, const recob::Vertex &center,
76  const geo::GeometryCore *geo, const detinfo::DetectorPropertiesData &dprop) {
77 
78  if (hits.size() == 0) return {-100., -100.};
79 
80  return HitPCAVec(hits, Vert2HitCoord(center, hits[0]->WireID(), geo, dprop), geo, dprop);
81 }
82 
83 std::array<float, 2> sbnpca::HitPCAVec(const std::vector<art::Ptr<recob::Hit>> &hits, std::array<float, 2> center,
84  const geo::GeometryCore *geo, const detinfo::DetectorPropertiesData &dprop) {
85 
86  if (hits.size() < 2) return {-100., -100.};
87 
88  std::array<float, 2> sum {};
89  for (const art::Ptr<recob::Hit> &h: hits) {
90  std::array<float, 2> vec = HitVector(*h, geo, dprop);
91  sum[0] += vec[0] - center[0];
92  sum[1] += vec[1] - center[1];
93  }
94  sum[0] = sum[0] / hits.size();
95  sum[1] = sum[1] / hits.size();
96 
97  std::array<std::array<float, 2>, 2> scatter {};
98  for (const art::Ptr<recob::Hit> &h: hits) {
99  std::array<float, 2> vec = HitVector(*h, geo, dprop);
100  vec[0] -= sum[0] - center[0];
101  vec[1] -= sum[1] - center[1];
102 
103  scatter[0][0] += vec[0] * vec[0];
104  scatter[0][1] += vec[0] * vec[1];
105  scatter[1][0] += vec[1] * vec[0];
106  scatter[1][1] += vec[1] * vec[1];
107  }
108 
109  // first get the eigenvalues of the matrix
110  float trace = scatter[0][0] + scatter[1][1];
111  float det = scatter[0][0] * scatter[1][1] - scatter[0][1] * scatter[1][0];
112 
113  // this is always the max-eigenvalue
114  float eigenP = (1. / 2.) * (trace + sqrt(trace*trace - 4 * det));
115  // float eigenM = (1. / 2.) * (trace - sqrt(trace*trace - 4 * det));
116 
117  // and then the eigenvectors
118  std::array<float, 2> ret {scatter[0][1], eigenP - scatter[0][0]};
119  // std::array<float, 2> eigenVM {scatter[0][1], eigenM - scatter[0][0]};
120 
121  // make sure the sign is right
122  if (sum[0] * ret[0] + sum[1] * ret[1] < 0.) {
123  ret[0] = -ret[0];
124  ret[1] = -ret[1];
125  }
126 
127  return ret;
128 
129 }
130 
131 std::array<float, 2> sbnpca::HitPCAEigen(const std::vector<art::Ptr<recob::Hit>> &hits, const art::Ptr<recob::Hit> &center,
132  const geo::GeometryCore *geo, const detinfo::DetectorPropertiesData &dprop) {
133 
134  std::array<float, 2> sum {};
135  for (const art::Ptr<recob::Hit> &h: hits) {
136  std::array<float, 2> vec = HitVector(*h, *center, geo, dprop);
137  sum[0] += vec[0];
138  sum[1] += vec[1];
139  }
140  sum[0] = sum[0] / hits.size();
141  sum[1] = sum[1] / hits.size();
142 
143  std::array<std::array<float, 2>, 2> scatter {};
144  for (const art::Ptr<recob::Hit> &h: hits) {
145  std::array<float, 2> vec = HitVector(*h, *center, geo, dprop);
146  vec[0] -= sum[0];
147  vec[1] -= sum[1];
148 
149  scatter[0][0] += vec[0] * vec[0];
150  scatter[0][1] += vec[0] * vec[1];
151  scatter[1][0] += vec[1] * vec[0];
152  scatter[1][1] += vec[1] * vec[1];
153  }
154 
155  // first get the eigenvalues of the matrix
156  float trace = scatter[0][0] + scatter[1][1];
157  float det = scatter[0][0] * scatter[1][1] - scatter[0][1] * scatter[1][0];
158 
159  float eigenP = (1. / 2.) * (trace + sqrt(trace*trace - 4 * det));
160  float eigenM = (1. / 2.) * (trace - sqrt(trace*trace - 4 * det));
161 
162  return {eigenP, eigenM};
163 }
164 
165 std::array<float, 2> sbnpca::Vert2HitCoord(const recob::Vertex &vert, const geo::PlaneID &planeID,
166  const geo::GeometryCore *geo, const detinfo::DetectorPropertiesData &dprop) {
167 
168  float vert_wire_coord = geo->WireCoordinate(vert.position(), planeID) * geo->WirePitch();
169  float vert_time_coord = vert.position().X();
170 
171  return {vert_wire_coord, vert_time_coord};
172 }
173 
175  float vert_wire_coord = geo->WireCoordinate(vert.position(), hit.WireID()) * geo->WirePitch();
176  float hit_wire_coord = hit.WireID().Wire * geo->WirePitch();
177 
178  float vert_time_coord = vert.position().X();
179  float hit_time_coord = dprop.ConvertTicksToX(hit.PeakTime(), hit.WireID());
180 
181  return sqrt((vert_wire_coord - hit_wire_coord) * (vert_wire_coord - hit_wire_coord) +
182  (vert_time_coord - hit_time_coord) * (vert_time_coord - hit_time_coord));
183 }
184 
185 
geo::Length_t WireCoordinate(double YPos, double ZPos, geo::PlaneID const &planeid) const
Returns the index of the nearest wire to the specified position.
float Vert2HitDistance(const recob::Hit &hit, const recob::Vertex &vert, const geo::GeometryCore *geo, const detinfo::DetectorPropertiesData &dprop)
Definition: PCA.cc:174
std::array< float, 2 > HitPCAVec(const std::vector< art::Ptr< recob::Hit >> &hits, const recob::Hit &center, const geo::GeometryCore *geo, const detinfo::DetectorPropertiesData &dprop)
Definition: PCA.cc:69
geo::WireID WireID() const
Definition: Hit.h:233
The data type to uniquely identify a Plane.
Definition: geo_types.h:472
WireID_t Wire
Index of the wire within its plane.
Definition: geo_types.h:580
process_name hit
Definition: cheaterreco.fcl:51
Definition of vertex object for LArSoft.
Definition: Vertex.h:35
geo::Length_t WirePitch(geo::PlaneID const &planeid) const
Returns the distance between two consecutive wires.
while getopts h
M::value_type trace(const M &m)
auto vector(Vector const &v)
Returns a manipulator which will print the specified array.
Definition: DumpUtils.h:265
double distance(geo::Point_t const &point, CathodeDesc_t const &cathode)
Returns the distance of a point from the cathode.
IDparameter< geo::WireID > WireID
Member type of validated geo::WireID parameter.
std::tuple< std::vector< art::Ptr< recob::Hit > >, std::vector< art::Ptr< recob::Hit > >, bool > GetNearestHits(const std::vector< art::Ptr< recob::Hit >> &hits, int ihit, float distance, const geo::GeometryCore *geo, const detinfo::DetectorPropertiesData &dprop)
Definition: PCA.cc:39
float VecAngle(std::array< float, 2 > A, std::array< float, 2 > B)
Definition: PCA.cc:5
float HitDistance(const recob::Hit &A, const recob::Hit &B, const geo::GeometryCore *geo, const detinfo::DetectorPropertiesData &dprop)
Definition: PCA.cc:34
Description of geometry of one entire detector.
double ConvertTicksToX(double ticks, int p, int t, int c) const
float PeakTime() const
Time of the signal peak, in tick units.
Definition: Hit.h:218
std::array< float, 2 > Vert2HitCoord(const recob::Vertex &vert, const geo::PlaneID &planeID, const geo::GeometryCore *geo, const detinfo::DetectorPropertiesData &dprop)
Definition: PCA.cc:165
2D representation of charge deposited in the TDC/wire plane
Definition: Hit.h:48
float A
Definition: dedx.py:137
const Point_t & position() const
Return vertex 3D position.
Definition: Vertex.h:60
std::array< float, 2 > HitPCAEigen(const std::vector< art::Ptr< recob::Hit >> &hits, const art::Ptr< recob::Hit > &center, const geo::GeometryCore *geo, const detinfo::DetectorPropertiesData &dprop)
Definition: PCA.cc:131
std::array< float, 2 > HitVector(const recob::Hit &A, const geo::GeometryCore *geo, const detinfo::DetectorPropertiesData &dprop)
Definition: PCA.cc:12