74 : theHitsMin_(iConfig.getParameter<
int>(
"HitsMin")),
75 thePruneCut_(iConfig.getParameter<double>(
"PruneCut")),
76 theTimeOffset_(iConfig.getParameter<double>(
"DTTimeOffset")),
77 theError_(iConfig.getParameter<double>(
"HitError")),
78 useSegmentT0_(iConfig.getParameter<
bool>(
"UseSegmentT0")),
79 doWireCorr_(iConfig.getParameter<
bool>(
"DoWireCorr")),
80 dropTheta_(iConfig.getParameter<
bool>(
"DropTheta")),
81 requireBothProjections_(iConfig.getParameter<
bool>(
"RequireBothProjections")),
82 debug(iConfig.getParameter<
bool>(
"debug")) {
84 theService = std::make_unique<MuonServiceProxy>(serviceParameters);
94 const std::vector<const DTRecSegment4D*>& segments,
99 std::cout <<
" *** DT Timimng Extractor ***" << std::endl;
121 std::vector<TimeMeasurement> tms;
122 for (
const auto& rechit : segments) {
124 DetId id = rechit->geographicalId();
128 std::cout <<
"Matched DT segment in station " << station << std::endl;
131 bool bothProjections = ((rechit->hasPhi()) && (rechit->hasZed()));
144 std::cout <<
" *** Segment t0: " << segm->
t0() << std::endl;
157 for (
const auto& hiti : hits1d) {
158 const GeomDet* dtcell = theTrackingGeometry->
idToDet(hiti.geographicalId());
161 std::pair<TrajectoryStateOnSurface, double> tsos;
165 double dist_straight = dtcell->
toGlobal(hiti.localPosition()).
mag();
166 if (tsos.first.isValid()) {
167 dist = tsos.second + posp.mag();
170 dist = dist_straight;
174 thisHit.
driftCell = hiti.geographicalId();
190 if (
doWireCorr_ && !bothProjections && tsos.first.isValid()) {
192 float propgL = layer->
toLocal(tsos.first.globalPosition()).
y();
193 float wirePropCorr = propgL / 24.4 * 0.00543;
195 wirePropCorr = -wirePropCorr;
199 tofCorr = (tofCorr / 29.979) * 0.00543;
205 float slCorr = (dist_straight - dist) / 29.979 * 0.00543;
214 tms.push_back(thisHit);
219 bool modified =
false;
220 std::vector<double> dstnc, local_t0, hitWeightTimeVtx, hitWeightInvbeta, left;
221 double totalWeightInvbeta = 0;
222 double totalWeightTimeVtx = 0;
229 hitWeightTimeVtx.clear();
230 hitWeightInvbeta.clear();
233 std::vector<int> hit_idx;
234 totalWeightInvbeta = 0;
235 totalWeightTimeVtx = 0;
238 for (
int sta = 1; sta < 5; sta++)
240 std::vector<TimeMeasurement> seg;
241 std::vector<int> seg_idx;
243 for (
auto& tm : tms) {
244 if ((tm.station == sta) && (tm.isPhi ==
phi)) {
246 seg_idx.push_back(tmpos);
251 unsigned int segsize = seg.size();
256 std::vector<double> hitxl, hitxr, hityl, hityr;
258 for (
auto& tm : seg) {
259 DetId id = tm.driftCell;
267 hitxl.push_back(celly);
268 hityl.push_back(tm.posInLayer);
270 hitxr.push_back(celly);
271 hityr.push_back(tm.posInLayer);
275 if (!
fitT0(a,
b, hitxl, hityl, hitxr, hityr)) {
277 std::cout <<
" t0 = zero, Left hits: " << hitxl.size() <<
" Right hits: " << hitxr.size() << std::endl;
282 if ((hitxl.empty()) || (hityl.empty()))
286 for (
const auto& tm : seg) {
287 DetId id = tm.driftCell;
293 double segmLocalPos =
b + layerZ *
a;
294 double hitLocalPos = tm.posInLayer;
295 int hitSide = -tm.isLeft * 2 + 1;
296 double t0_segm = (-(hitSide * segmLocalPos) + (hitSide * hitLocalPos)) / 0.00543 + tm.timeCorr;
299 std::cout <<
" Segm hit. dstnc: " << tm.distIP <<
" t0: " << t0_segm << std::endl;
301 dstnc.push_back(tm.distIP);
302 local_t0.push_back(t0_segm);
303 left.push_back(hitSide);
304 hitWeightInvbeta.push_back(((
double)seg.size() - 2.) * tm.distIP * tm.distIP /
306 hitWeightTimeVtx.push_back(((
double)seg.size() - 2.) / ((double)seg.size() *
theError_ *
theError_));
307 hit_idx.push_back(seg_idx.at(segidx));
309 totalWeightInvbeta += ((double)seg.size() - 2.) * tm.distIP * tm.distIP /
311 totalWeightTimeVtx += ((double)seg.size() - 2.) / ((double)seg.size() *
theError_ *
theError_);
315 if (totalWeightInvbeta == 0)
320 std::cout <<
" Points for global fit: " << dstnc.size() << std::endl;
322 double invbeta = 0, invbetaErr = 0;
323 double timeVtx = 0, timeVtxErr = 0;
325 for (
unsigned int i = 0;
i < dstnc.size();
i++) {
326 invbeta += (1. + local_t0.at(
i) / dstnc.at(
i) * 30.) * hitWeightInvbeta.at(
i) / totalWeightInvbeta;
327 timeVtx += local_t0.at(
i) * hitWeightTimeVtx.at(
i) / totalWeightTimeVtx;
331 std::vector<TimeMeasurement>::iterator tmmax;
334 double diff_ibeta, diff_tvtx;
335 for (
unsigned int i = 0;
i < dstnc.size();
i++) {
336 diff_ibeta = (1. + local_t0.at(
i) / dstnc.at(
i) * 30.) - invbeta;
337 diff_ibeta = diff_ibeta * diff_ibeta * hitWeightInvbeta.at(
i);
338 diff_tvtx = local_t0.at(
i) - timeVtx;
339 diff_tvtx = diff_tvtx * diff_tvtx * hitWeightTimeVtx.at(
i);
340 invbetaErr += diff_ibeta;
341 timeVtxErr += diff_tvtx;
345 if (diff_tvtx > chimax) {
346 tmmax = tms.begin() + hit_idx.at(
i);
358 double cf = 1. / (dstnc.size() - 1);
359 invbetaErr =
sqrt(invbetaErr / totalWeightInvbeta * cf);
360 timeVtxErr =
sqrt(timeVtxErr / totalWeightTimeVtx * cf);
361 std::cout <<
" Measured 1/beta: " << invbeta <<
" +/- " << invbetaErr << std::endl;
362 std::cout <<
" Measured time: " << timeVtx <<
" +/- " << timeVtxErr << std::endl;
367 for (
unsigned int i = 0;
i < dstnc.size();
i++) {
368 tmSequence.
dstnc.push_back(dstnc.at(
i));
369 tmSequence.
local_t0.push_back(local_t0.at(
i));
387 std::cout <<
" The muon track matches " << range.size() <<
" segments." << std::endl;
388 fillTiming(tmSequence, range, muonTrack, iEvent, iSetup);
393 const std::vector<double>& xl,
394 const std::vector<double>& yl,
395 const std::vector<double>& xr,
396 const std::vector<double>& yr) {
397 double sx = 0,
sy = 0, sxy = 0, sxx = 0, ssx = 0, ssy = 0,
s = 0,
ss = 0;
399 for (
unsigned int i = 0;
i < xl.size();
i++) {
402 sxy += xl[
i] * yl[
i];
403 sxx += xl[
i] * xl[
i];
410 for (
unsigned int i = 0;
i < xr.size();
i++) {
413 sxy += xr[
i] * yr[
i];
414 sxx += xr[
i] * xr[
i];
421 double delta =
ss *
ss * sxx +
s * sx * sx +
s * ssx * ssx -
s *
s * sxx - 2 *
ss * sx * ssx;
426 a = (ssy *
s * ssx + sxy *
ss *
ss +
sy * sx *
s -
sy *
ss * ssx - ssy * sx *
ss - sxy *
s *
s) / delta;
427 b = (ssx *
sy * ssx + sxx * ssy *
ss + sx * sxy *
s - sxx *
sy *
s - ssx * sxy *
ss - sx * ssy * ssx) / delta;
428 t0_corr = (ssx *
s * sxy + sxx *
ss *
sy + sx * sx * ssy - sxx *
s * ssy - sx *
ss * sxy - ssx * sx *
sy) / delta;
T getParameter(std::string const &) const
std::vector< double > local_t0
T mag() const
The vector magnitude. Equivalent to sqrt(vec.mag2())
GlobalPoint toGlobal(const Local2DPoint &lp) const
Conversion to the global R.F. from the R.F. of the GeomDet.
double totalWeightTimeVtx
LocalPoint toLocal(const GlobalPoint &gp) const
Conversion to the R.F. of the GeomDet.
const Plane & surface() const
The nominal surface of the GeomDet.
const Surface::PositionType & position() const
The position (origin of the R.F.)
virtual std::pair< TrajectoryStateOnSurface, double > propagateWithPath(const FreeTrajectoryState &, const Surface &) const final
edm::ESHandle< GlobalTrackingGeometry > theTrackingGeometry
std::vector< double > weightInvbeta
std::vector< DTRecHit1D > specificRecHits() const
Access to specific components.
double totalWeightInvbeta
XYZVectorD XYZVector
spatial vector with cartesian internal representation
XYZPointD XYZPoint
point in space with cartesian internal representation
std::vector< double > weightTimeVtx
const DTSuperLayer * superLayer() const
const GeomDet * idToDet(DetId) const override
std::vector< const DTRecSegment4D * > matchDT(const reco::Track &muon, const edm::Event &event)
perform the matching
const DTLayer * layer(const DTLayerId &id) const
Return a layer given its id.
DetId geographicalId() const
double t0() const
Get the segment t0 (if recomputed, 0 is returned otherwise)
int station() const
Return the station number.
std::vector< double > dstnc
const PositionType & position() const
T const * product() const