Go to the documentation of this file.00001 #include "RecoVertex/GaussianSumVertexFit/interface/GsfVertexUpdator.h"
00002 #include "RecoVertex/GaussianSumVertexFit/interface/BasicMultiVertexState.h"
00003 #include "FWCore/MessageLogger/interface/MessageLogger.h"
00004 #include <cfloat>
00005
00006 GsfVertexUpdator::GsfVertexUpdator(bool limit, const GsfVertexMerger * merger) :
00007 limitComponents (limit)
00008 {
00009 if (limitComponents) theMerger = merger->clone();
00010 }
00011
00012
00013 CachingVertex<5> GsfVertexUpdator::add(const CachingVertex<5> & oldVertex,
00014 const RefCountedVertexTrack track) const
00015 {
00016
00017 VSC prevVtxComponents = oldVertex.vertexState().components();
00018
00019
00020
00021
00022
00023 if (prevVtxComponents.empty()) {
00024 throw VertexException
00025 ("GsfVertexUpdator::(Previous) Vertex to update has no components");
00026 }
00027
00028 LTC ltComponents = track->linearizedTrack()->components();
00029 if (ltComponents.empty()) {
00030 throw VertexException
00031 ("GsfVertexUpdator::Track to add to vertex has no components");
00032 }
00033
00034 if ((ltComponents.size()==1) && (prevVtxComponents.size()==1))
00035 return kalmanVertexUpdator.add(oldVertex, track);
00036
00037 float trackWeight = track->weight();
00038
00039 std::vector<VertexComponent> newVertexComponents;
00040 newVertexComponents.reserve(prevVtxComponents.size()*ltComponents.size());
00041
00042
00043
00044
00045
00046
00047 for (VSC::iterator vertexCompIter = prevVtxComponents.begin();
00048 vertexCompIter != prevVtxComponents.end(); vertexCompIter++ ) {
00049 for (LTC::iterator trackCompIter = ltComponents.begin();
00050 trackCompIter != ltComponents.end(); trackCompIter++ ) {
00051 newVertexComponents.push_back(
00052 createNewComponent(*vertexCompIter, *trackCompIter, trackWeight, +1));
00053
00054 if (!newVertexComponents.back().first.isValid()) return CachingVertex<5>();
00055 }
00056 }
00057
00058
00059
00060
00061 std::vector<RefCountedVertexTrack> newVertexTracks = oldVertex.tracks();
00062 newVertexTracks.push_back(track);
00063
00064
00065
00066
00067 VertexChi2Pair vertexChi2Pair = assembleVertexComponents(newVertexComponents);
00068
00069 VertexState newVertexState = vertexChi2Pair.first;
00070
00071 double chi2 = oldVertex.totalChiSquared() + vertexChi2Pair.second;
00072
00073
00074 if (limitComponents) newVertexState = theMerger->merge(newVertexState);
00075
00076 if (oldVertex.hasPrior()) {
00077 return CachingVertex<5>(oldVertex.priorPosition(), oldVertex.priorError(),
00078 newVertexState.weightTimesPosition(),
00079 newVertexState.weight(), newVertexTracks, chi2);
00080 } else {
00081 return CachingVertex<5>(newVertexState, newVertexTracks, chi2);
00082 }
00083
00084
00085 }
00086
00087
00088
00089
00090 CachingVertex<5> GsfVertexUpdator::remove(const CachingVertex<5> & oldVertex,
00091 const RefCountedVertexTrack track) const
00092 {
00093 throw VertexException("GsfVertexUpdator::Remove Methode not yet done");
00094
00095 }
00096
00097
00103 GsfVertexUpdator::VertexComponent
00104 GsfVertexUpdator::createNewComponent(const VertexState & oldVertex,
00105 const RefCountedLinearizedTrackState linTrack, float weight, int sign) const
00106 {
00107
00108 if(abs(sign) != 1)
00109 throw VertexException ("GsfVertexUpdator::sign not equal to 1.");
00110
00111 if(sign == -1)
00112 throw VertexException("GsfVertexUpdator::sign of -1 not yet implemented.");
00113
00114
00115
00116 double weightInMixture = theWeightCalculator.calculate(oldVertex, linTrack, 1.E9);
00117 if (weightInMixture < 0.) return VertexComponent(VertexState(), WeightChi2Pair(0.,0.));
00118
00119
00120 VertexState newVertex = kalmanVertexUpdator.positionUpdate(oldVertex,
00121 linTrack, weight, sign);
00122 if (!newVertex.isValid()) return VertexComponent(newVertex, WeightChi2Pair(0.,0.));
00123
00124
00125 std::pair <bool, double> chi2P = kalmanVertexUpdator.chi2Increment(oldVertex, newVertex,
00126 linTrack, weight);
00127 if (!chi2P.first) return VertexComponent(VertexState(), WeightChi2Pair(0.,0.));
00128
00129
00130
00131 return VertexComponent(newVertex, WeightChi2Pair(weightInMixture, chi2P.second));
00132 }
00133
00134 GsfVertexUpdator::VertexChi2Pair GsfVertexUpdator::assembleVertexComponents(
00135 const std::vector<GsfVertexUpdator::VertexComponent> & newVertexComponents) const
00136 {
00137 VSC vertexComponents;
00138 vertexComponents.reserve(newVertexComponents.size());
00139
00140
00141
00142 double totalWeight = 0.;
00143 double totalChi2 = 0.;
00144
00145 for (std::vector<VertexComponent>::const_iterator iter = newVertexComponents.begin();
00146 iter != newVertexComponents.end(); iter ++) {
00147 totalWeight += iter->second.first;
00148 }
00149
00150 if (totalWeight<DBL_MIN) {
00151 edm::LogWarning("GsfVertexUpdator") << "Updated Vertex has total weight of 0. "
00152 <<"The track is probably very far away.";
00153 return VertexChi2Pair( VertexState(), 0.);
00154 }
00155
00156 for (std::vector<VertexComponent>::const_iterator iter = newVertexComponents.begin();
00157 iter != newVertexComponents.end(); iter ++) {
00158 double weight = iter->second.first/totalWeight;
00159 if (iter->second.first>DBL_MIN) {
00160 vertexComponents.push_back(VertexState(iter->first.weightTimesPosition(),
00161 iter->first.weight(), weight));
00162 totalChi2 += iter->second.second * weight;
00163 }
00164 }
00165
00166
00167
00168 if (vertexComponents.empty()){
00169 edm::LogWarning("GsfVertexUpdator") << "No Vertex State left after reweighting.";
00170 return VertexChi2Pair( VertexState(), 0.);
00171 }
00172
00173 return VertexChi2Pair( VertexState( new BasicMultiVertexState( vertexComponents)),
00174 totalChi2);
00175 }