#include <AlgShowerSR.h>
Inheritance diagram for AlgShowerSR:

Public Member Functions | |
| AlgShowerSR () | |
| virtual | ~AlgShowerSR () |
| virtual void | RunAlg (AlgConfig &ac, CandHandle &ch, CandContext &cx) |
| virtual void | Trace (const char *c) const |
Protected Member Functions | |
| void | SetUV (CandShowerHandle *) |
| Int_t | FindTimingDirection (CandShowerHandle &shwh, AlgConfig &ac, Double_t *fitparm, Double_t &timefitchi2) |
|
|
Within AlgShowerSR::RunAlg, the vertex location and shower direction is determined. First, the most upstream U and V planes are found. Next, a loop over all shower clusters is used to obtain the total shower charge. The charge-weighted U/V positions of the CandClusters in the plane interval from the most upstream planes to VtxPlaneSpan planes downstream is identified as the shower vertex location. To obtain the shower direction, a linear fit is performed to the charge-weighted transverse position in a given plane vs the Z position of that plane. A weighted linear fit is performed in each viewed, weighted by the total cluster charge for this shower in a given plane. The du/dz and dv/dz slopes obtained in these fits are then used to obtain the direction cosines of the shower axis. Finally, the shower energy is set. Definition at line 41 of file AlgShowerSR.cxx. 00042 {
00043 }
|
|
|
Definition at line 46 of file AlgShowerSR.cxx. 00047 {
00048 }
|
|
||||||||||||||||||||
|
Definition at line 645 of file AlgShowerSR.cxx. References DetectorType::AsString(), UgliStripHandle::ClearFiber(), CandDigitHandle::GetCharge(), CandHandle::GetDaughterIterator(), VldContext::GetDetector(), Registry::GetDouble(), PlexSEIdAltL::GetEnd(), UgliStripHandle::GetHalfLength(), Registry::GetInt(), CandHandle::GetNDaughters(), CandStripHandle::GetPlane(), CandStripHandle::GetPlaneView(), CandDigitHandle::GetPlexSEIdAltL(), CandStripHandle::GetStripEndId(), UgliGeomHandle::GetStripHandle(), CandStripHandle::GetTime(), CandShowerHandle::GetU(), CandShowerHandle::GetV(), CandHandle::GetVldContext(), CandStripHandle::GetZPos(), MSG, PropagationVelocity::Velocity(), LinearFit::Weighted(), and UgliStripHandle::WlsPigtail(). Referenced by RunAlg(). 00649 {
00650 Double_t parmMaxTimeFitRes = ac.GetDouble("MaxTimeFitRes");
00651 Double_t parmMinTimeFitSize = ac.GetInt("MinTimeFitSize");
00652 Double_t parmMaxTimeFitOutlier = ac.GetDouble("MaxTimeFitOutlier");
00653
00654 MSG("AlgShowerSR", Msg::kVerbose) << "in find timing direction" << endl;
00655
00656 fitparm[0] = 0;
00657 fitparm[1] = 0;
00658
00659 CandStripHandle *strip = 0;
00660 CandDigitHandle *digit = 0;
00661
00662 StripEnd::StripEnd_t stripEnd = StripEnd::kUnknown;
00663
00664 //get VldContext and UgliGeomHandle
00665 CandStripHandleItr stripItr(shwh.GetDaughterIterator());
00666 CandStripHandle *firststrip = stripItr.Ptr();
00667
00668 assert(firststrip);
00669
00670 const VldContext *vldcontext = firststrip->GetVldContext();
00671 assert(vldcontext);
00672
00673 UgliGeomHandle ugh(*vldcontext);
00674
00675 //arrays for determining the timing direction - limit to
00676 //1000 entries - really shouldnt need more than that to
00677 //be able to figure out if the shower is going north or
00678 //south
00679 Double_t time[1000];
00680 Double_t pathLength[1000];
00681 Double_t weight[1000];
00682 Double_t adcsum[1000];
00683
00684 for(Int_t i = 0; i<1000; ++i){
00685 time[i] = 0.;
00686 pathLength[i] = 0.;
00687 weight[i] = 0.;
00688 adcsum[i] = 0;
00689 }
00690
00691 //need to put in a check to make sure you dont have more planes in one
00692 //view than the other
00693 Int_t uBeg = 1000;
00694 Int_t uEnd = 0;
00695 Int_t vBeg = 1000;
00696 Int_t vEnd = 0;
00697 while( (strip = stripItr())){
00698 Int_t plane = strip->GetPlane();
00699 if(strip->GetPlaneView() == PlaneView::kV && plane>vEnd) vEnd=plane;
00700 if(strip->GetPlaneView() == PlaneView::kV && plane<vBeg) vBeg=plane;
00701 if(strip->GetPlaneView() == PlaneView::kU && plane>uEnd) uEnd=plane;
00702 if(strip->GetPlaneView() == PlaneView::kU && plane<uBeg) uBeg=plane;
00703 }
00704
00705 //get the endpoints
00706 Int_t showerBeg = TMath::Min(uBeg,vBeg);
00707 Int_t showerEnd = TMath::Max(uEnd,vEnd);
00708
00709 if(TMath::Abs(uBeg-vBeg)>3.){
00710 showerBeg = TMath::Max(uBeg,vBeg) - 1;
00711 }
00712 if(TMath::Abs(uEnd-vEnd)>3.){
00713 showerEnd = TMath::Min(uEnd,vEnd) + 1;
00714 }
00715 MSG("AlgShowerSR", Msg::kDebug) << "u end points = " << uBeg
00716 << " " << uEnd << " v end points = "
00717 << vBeg << " " << vEnd << endl
00718 << " shower end points = " << showerBeg
00719 << " " << showerEnd << endl;
00720 Double_t halfLength = 0.;
00721 Double_t apos = 0.;
00722 Double_t distFromCenter = 0.;
00723 Double_t fiberDist = 0.;
00724 Int_t nctr = 0;
00725 Double_t maxPathLength = 0;
00726 for(Int_t iplane = showerBeg;iplane <= showerEnd;iplane++){
00727 adcsum[nctr] = 0;
00728 time[nctr] = 0;
00729 pathLength[nctr] = 0;
00730 CandStripHandleItr shwstripItr(shwh.GetDaughterIterator());
00731 while( (strip = shwstripItr()) && nctr<1000){
00732 if(strip->GetPlane() == iplane){
00733 MSG("AlgShowerSR", Msg::kDebug) << "strip from plane " << iplane
00734 << " " << DetectorType::AsString(vldcontext->GetDetector()) << endl;
00735
00736 //only look at double ended strips if in the far detector
00737 //and strips from planes that have orthogonal measurements
00738 if( (strip->GetNDaughters() == 2 || vldcontext->GetDetector() == DetectorType::kNear)){
00739
00740 MSG("AlgShowerSR", Msg::kVerbose) << "strip good for timing" << endl;
00741
00742 //get the iterator over the digits in the strip
00743 CandDigitHandleItr digitItr(strip->GetDaughterIterator());
00744
00745 while( (digit = digitItr())){
00746 stripEnd = digit->GetPlexSEIdAltL().GetEnd();
00747 pathLength[nctr] = strip->GetZPos();
00748 maxPathLength = TMath::Max(maxPathLength,pathLength[nctr] );
00749 UgliStripHandle stripHandle = ugh.GetStripHandle(strip->GetStripEndId());
00750 halfLength = stripHandle.GetHalfLength();
00751 apos = 0.;
00752 fiberDist = 0.;
00753
00754 if(strip->GetPlaneView() == PlaneView::kV) apos = shwh.GetU(iplane);
00755 else if(strip->GetPlaneView() == PlaneView::kU) apos = shwh.GetV(iplane);
00756 distFromCenter = 0.;
00757 if(strip->GetPlaneView() == PlaneView::kV)
00758 distFromCenter = (stripEnd == StripEnd::kNegative) ? apos : -apos;
00759 else if(strip->GetPlaneView() == PlaneView::kU)
00760 distFromCenter = (stripEnd == StripEnd::kNegative) ? -apos : apos;
00761
00762 fiberDist = (halfLength + distFromCenter + stripHandle.ClearFiber(stripEnd)
00763 + stripHandle.WlsPigtail(stripEnd));
00764
00765 time[nctr] += digit->GetCharge() * (strip->GetTime(stripEnd) - fiberDist/PropagationVelocity::Velocity());
00766
00767 weight[nctr] = 1.0;
00768 adcsum[nctr] += digit->GetCharge();
00769 Double_t temptime = time[nctr];
00770 if(adcsum[nctr]!=0)temptime /= adcsum[nctr];
00771 MSG("AlgShowerSR", Msg::kDebug) << nctr
00772 << " " << pathLength[nctr]
00773 << " " << temptime
00774 << " " << strip->GetTime(stripEnd)
00775 << " " << weight[nctr]
00776 << endl;
00777
00778 }//end loop over digits in strip
00779 }//end if double ended strip
00780 }//end loop over strips in plane
00781 }
00782 if(adcsum[nctr] > 0){
00783 time[nctr] /= adcsum[nctr];
00784 nctr++;
00785 }
00786 }
00787 for(Int_t i=0;i<nctr;i++){
00788 MSG("AlgShowerSR",Msg::kDebug) << "TIMEFIT " << i << " "
00789 <<pathLength[i] << " "
00790 << (time[i]-time[0])*1.e9 << " " << weight[i] << endl;
00791 }
00792
00793 //loop over all strips in the shower
00794 Double_t efitparm[2];
00795 Double_t maxresid = parmMaxTimeFitRes + 1.;
00796 Double_t resid = 0.;
00797 Int_t ctr = nctr;
00798 Int_t imaxresid = 0;
00799 Int_t nremove = 0;
00800 Bool_t dofit = false;
00801 while(maxresid > parmMaxTimeFitRes
00802 && nctr-nremove > parmMinTimeFitSize
00803 && (1.*nremove) < parmMaxTimeFitOutlier*nctr
00804 ){
00805 dofit = true;
00806 LinearFit::Weighted(ctr,pathLength,time,weight,fitparm,efitparm);
00807 maxresid = 0.;
00808 imaxresid = 0;
00809 for(int i=0; i<ctr; ++i){
00810 resid = (fitparm[1]*pathLength[i]+fitparm[0]-time[i])*1.e9;
00811 if(weight[i]>0. && TMath::Abs(resid)>maxresid){
00812 maxresid = TMath::Abs(resid);
00813 imaxresid = i;
00814 }
00815 }
00816
00817 MSG("AlgShowerSR",Msg::kDebug) << "constrained fit, dt/ds slope, offset = "
00818 << fitparm[1] << " " << fitparm[0] << endl;
00819 MSG("AlgShowerSR",Msg::kDebug) << "maximum residual " << maxresid << " "
00820 << pathLength[imaxresid] << " "
00821 << time[imaxresid] << " "
00822 << weight[imaxresid] << endl;
00823
00824 if(maxresid>parmMaxTimeFitRes){
00825 MSG("AlgShowerSR",Msg::kDebug) << " removing" << endl;
00826 weight[imaxresid] = 0.;
00827 nremove++;
00828 }
00829
00830 timefitchi2 = 0.;
00831 for(int i = 0; i < ctr; ++i){
00832 resid = (fitparm[1]*pathLength[i]+fitparm[0]-time[i])*1e9;
00833 timefitchi2 += weight[i]*resid*resid;
00834 }
00835 MSG("AlgShowerSR",Msg::kDebug) << "chi2 = " << timefitchi2 \
00836 << " n = " << nctr-nremove << endl;
00837 }//end loop to find timing fit and remove outliers
00838
00839 timefitchi2 = 0.;
00840 if(dofit){
00841 for(int i = 0; i<ctr; ++i){
00842 if(weight[i] > 0.){
00843 resid = (fitparm[1]*pathLength[i]+fitparm[0]-time[i])*1.e9;
00844 timefitchi2 += weight[i]*resid*resid;
00845 }
00846 }
00847 }
00848
00849 MSG("AlgShowerSR",Msg::kDebug) << " TIMEFIT " << fitparm[1]
00850 << " chi^2/ndf = "
00851 << timefitchi2/(1.*(nctr-nremove))
00852 << " " << TMath::Abs(uBeg-uEnd)
00853 << " " << TMath::Abs(vBeg-vEnd) << endl;
00854
00855 //check the chi^2 for the fit - if it is really bad dont change the
00856 //initial guess at the direction for the event, ie just make sure
00857 //that the slope in time vs pathlength is positive;
00858 if(fitparm[1] < 0. && timefitchi2 >= 10.*(nctr-nremove))
00859 fitparm[1] *= -1.;
00860 return nctr-nremove;
00861 }
|
|
||||||||||||||||
|
Implements AlgBase. Reimplemented in AlgShowerSS. Definition at line 51 of file AlgShowerSR.cxx. References CandShowerHandle::AddCluster(), CandHandle::AddDaughterLink(), AlgReco::Calibrate(), CandShowerHandle::CalibrateEnergy(), FindTimingDirection(), CandClusterHandle::GetBegPlane(), CandStripHandle::GetBegTime(), CandStripHandle::GetCharge(), CandContext::GetDataIn(), CandHandle::GetDaughterIterator(), CandRecoHandle::GetEndPlane(), CandClusterHandle::GetEndPlane(), CandRecoHandle::GetEndT(), CandRecoHandle::GetEndZ(), Registry::GetInt(), CandStripHandle::GetPlane(), CandStripHandle::GetPlaneView(), CandClusterHandle::GetPlaneView(), UgliGeomHandle::GetScintPlnHandle(), CandStripHandle::GetStripEndId(), CandStripHandle::GetTPos(), CandShowerHandle::GetU(), CandShowerHandle::GetV(), CandHandle::GetVldContext(), CandRecoHandle::GetVtxPlane(), CandRecoHandle::GetVtxT(), CandRecoHandle::GetVtxZ(), UgliPlnHandle::GetZ0(), MSG, CandRecoHandle::SetDirCosU(), CandRecoHandle::SetDirCosV(), CandRecoHandle::SetDirCosZ(), CandRecoHandle::SetEndDirCosU(), CandRecoHandle::SetEndDirCosV(), CandRecoHandle::SetEndDirCosZ(), CandRecoHandle::SetEndPlane(), CandRecoHandle::SetEndT(), CandRecoHandle::SetEndU(), CandRecoHandle::SetEndV(), CandRecoHandle::SetEndZ(), CandShowerHandle::SetEnergy(), SetUV(), CandRecoHandle::SetVtxPlane(), CandRecoHandle::SetVtxT(), CandRecoHandle::SetVtxU(), CandRecoHandle::SetVtxV(), CandRecoHandle::SetVtxZ(), and LinearFit::Weighted(). 00052 {
00053
00054 assert(ch.InheritsFrom("CandShowerHandle"));
00055 CandShowerHandle &csh = dynamic_cast<CandShowerHandle &>(ch);
00056
00057 assert(cx.GetDataIn());
00058 assert(cx.GetDataIn()->InheritsFrom("TObjArray"));
00059
00060 // grab parameters
00061
00062 // Double_t MIPperGeV = ac.GetDouble("MIPperGeV");
00063 Int_t vtxplanespan = ac.GetInt("VtxPlaneSpan");
00064 Int_t isCosmic = ac.GetInt("IsCosmic");
00065
00066 const TObjArray *tary =
00067 dynamic_cast<const TObjArray*>(cx.GetDataIn());
00068
00069 Int_t ubegplane=0;
00070 Int_t vbegplane=0;
00071 Int_t uendplane=0;
00072 Int_t vendplane=0;
00073 CandStripHandle *begstrip=0;
00074 CandStripHandle *endstrip=0;
00075
00076 for (Int_t i=0; i<=tary->GetLast(); i++) {
00077 TObject *tobj = tary->At(i);
00078 assert(tobj->InheritsFrom("CandClusterHandle"));
00079 CandClusterHandle *clusterhandle =
00080 dynamic_cast<CandClusterHandle*>(tobj);
00081 csh.AddCluster(clusterhandle);
00082 switch (clusterhandle->GetPlaneView()) {
00083 case PlaneView::kU:
00084 if (!ubegplane || clusterhandle->GetBegPlane()<ubegplane) {
00085 ubegplane = clusterhandle->GetBegPlane();
00086 }
00087 if(!uendplane || clusterhandle->GetEndPlane()>uendplane) {
00088 uendplane = clusterhandle->GetEndPlane();
00089 }
00090 break;
00091 case PlaneView::kV:
00092 if (!vbegplane || clusterhandle->GetBegPlane()<vbegplane) {
00093 vbegplane = clusterhandle->GetBegPlane();
00094 }
00095 if(!vendplane || clusterhandle->GetEndPlane()>vendplane) {
00096 vendplane = clusterhandle->GetEndPlane();
00097 }
00098 break;
00099 default:
00100 break;
00101 }
00102 if (!begstrip) {
00103 CandStripHandleItr stripItr(clusterhandle->GetDaughterIterator());
00104 begstrip = stripItr();
00105 }
00106 }
00107
00108 // bail if these shower has an empty daughter list
00109 if(!begstrip){
00110 MSG("ShowerSR", Msg::kError)
00111 << "Found empty daughter list in CandShowerSR" << endl;
00112 csh.SetDirCosU(0.);
00113 csh.SetDirCosV(0.);
00114 csh.SetDirCosZ(1.);
00115 csh.SetVtxPlane(-1);
00116 csh.SetVtxZ(-1.);
00117 csh.SetVtxU(0.);
00118 csh.SetVtxV(0.);
00119 csh.SetVtxT(0.);
00120 csh.SetEndZ(-1.);
00121 csh.SetEndU(0.);
00122 csh.SetEndV(0.);
00123 csh.SetEndT(0.);
00124 csh.SetEnergy(0);
00125
00126 return;
00127 }
00128
00129 const VldContext * vld = begstrip->GetVldContext();
00130 UgliGeomHandle ugh(*vld);
00131
00132 begstrip = 0;
00133
00134 Double_t uvtx=0.;
00135 Double_t vvtx=0.;
00136 Double_t uvtxph=0.;
00137 Double_t vvtxph=0.;
00138 Double_t tvtx=0.;
00139
00140 Double_t uend=0.;
00141 Double_t vend=0.;
00142 Double_t uendph=0.;
00143 Double_t vendph=0.;
00144 Double_t tend=0.;
00145
00146 Bool_t firstvtx(1);
00147 Bool_t firstend(1);
00148
00149 Double_t *uvtxfit = new Double_t[vtxplanespan+1];
00150 Double_t *uvtxphfit = new Double_t[vtxplanespan+1];
00151 Double_t *uvtxzfit = new Double_t[vtxplanespan+1];
00152 Double_t *vvtxfit = new Double_t[vtxplanespan+1];
00153 Double_t *vvtxphfit = new Double_t[vtxplanespan+1];
00154 Double_t *vvtxzfit = new Double_t[vtxplanespan+1];
00155
00156 Double_t *uendfit = new Double_t[vtxplanespan+1];
00157 Double_t *uendphfit = new Double_t[vtxplanespan+1];
00158 Double_t *uendzfit = new Double_t[vtxplanespan+1];
00159 Double_t *vendfit = new Double_t[vtxplanespan+1];
00160 Double_t *vendphfit = new Double_t[vtxplanespan+1];
00161 Double_t *vendzfit = new Double_t[vtxplanespan+1];
00162
00163 for (Int_t i=0; i<=vtxplanespan; i++) {
00164 uvtxfit[i] = 0.;
00165 uvtxphfit[i] = 0.;
00166 uvtxzfit[i] = 0.;
00167 vvtxfit[i] = 0.;
00168 vvtxphfit[i] = 0.;
00169 vvtxzfit[i] = 0.;
00170 uendfit[i] = 0.;
00171 uendphfit[i] = 0.;
00172 uendzfit[i] = 0.;
00173 vendfit[i] = 0.;
00174 vendphfit[i] = 0.;
00175 vendzfit[i] = 0.;
00176 }
00177
00178 // loop over cluster daughters, calculating a charge sum, and
00179 // constructing arrays of charge-weighted u vs z and v vs z for the
00180 // planes within VtxPlaneSpan of beginning and end of shower
00181
00182 Double_t charge=0.;
00183 for (Int_t i=0; i<=tary->GetLast(); i++) {
00184 TObject *tobj = tary->At(i);
00185 assert(tobj->InheritsFrom("CandClusterHandle"));
00186 CandClusterHandle *clusterhandle =
00187 dynamic_cast<CandClusterHandle*>(tobj);
00188 CandStripHandleItr stripItr(clusterhandle->GetDaughterIterator());
00189 while (CandStripHandle *strip = stripItr()) {
00190 csh.AddDaughterLink(*strip);
00191 charge += strip->GetCharge();
00192 if (!begstrip || strip->GetPlane()<begstrip->GetPlane()) {
00193 begstrip = strip;
00194 }
00195 if (!endstrip || strip->GetPlane()>endstrip->GetPlane()) {
00196 endstrip = strip;
00197 }
00198
00199 switch (strip->GetPlaneView()) {
00200 case PlaneView::kU:
00201 if (strip->GetPlane()<=ubegplane+vtxplanespan) {
00202 Double_t charge = strip->GetCharge();
00203 Double_t tpos = strip->GetTPos();
00204 uvtx += tpos*charge;
00205 uvtxph += charge;
00206 if (firstvtx || strip->GetBegTime()<tvtx) {
00207 firstvtx = 0;
00208 tvtx = strip->GetBegTime();
00209 }
00210 Int_t dplane = strip->GetPlane()-ubegplane;
00211 if(dplane<=vtxplanespan && dplane>+0){
00212 uvtxfit[dplane] += tpos*charge;
00213 uvtxphfit[dplane] += charge;
00214 UgliScintPlnHandle upid =
00215 ugh.GetScintPlnHandle(strip->GetStripEndId());
00216 uvtxzfit[dplane] = upid.GetZ0();
00217 }
00218 }
00219 if(strip->GetPlane()>=uendplane-vtxplanespan) {
00220 Double_t charge = strip->GetCharge();
00221 Double_t tpos = strip->GetTPos();
00222 uend += tpos*charge;
00223 uendph += charge;
00224 if (firstend || strip->GetBegTime()<tend) {
00225 firstend = 0;
00226 tend = strip->GetBegTime();
00227 }
00228 Int_t dplane = uendplane-strip->GetPlane();
00229 if(dplane<=vtxplanespan && dplane>=0){
00230 uendfit[dplane] += tpos*charge;
00231 uendphfit[dplane] += charge;
00232 UgliScintPlnHandle upid =
00233 ugh.GetScintPlnHandle(strip->GetStripEndId());
00234 uendzfit[dplane] = upid.GetZ0();
00235 }
00236 }
00237 break;
00238 case PlaneView::kV:
00239 if (strip->GetPlane()<=vbegplane+vtxplanespan) {
00240 Double_t charge = strip->GetCharge();
00241 Double_t tpos = strip->GetTPos();
00242 vvtx += tpos*charge;
00243 vvtxph += charge;
00244 if (firstvtx || strip->GetBegTime()<tvtx) {
00245 firstvtx = 0;
00246 tvtx = strip->GetBegTime();
00247 }
00248 Int_t dplane = strip->GetPlane()-vbegplane;
00249 if(dplane<=vtxplanespan && dplane>=0){
00250 vvtxfit[dplane] += tpos*charge;
00251 vvtxphfit[dplane] += charge;
00252 UgliScintPlnHandle upid =
00253 ugh.GetScintPlnHandle(strip->GetStripEndId());
00254 vvtxzfit[dplane] = upid.GetZ0();
00255 }
00256 }
00257 if(strip->GetPlane()>=uendplane-vtxplanespan) {
00258 Double_t charge = strip->GetCharge();
00259 Double_t tpos = strip->GetTPos();
00260 vend += tpos*charge;
00261 vendph += charge;
00262 if (firstend || strip->GetBegTime()<tend) {
00263 firstend = 0;
00264 tend = strip->GetBegTime();
00265 }
00266 Int_t dplane = vendplane-strip->GetPlane();
00267 if(dplane<=vtxplanespan && dplane>=0){
00268 vendfit[dplane] += tpos*charge;
00269 vendphfit[dplane] += charge;
00270 UgliScintPlnHandle upid =
00271 ugh.GetScintPlnHandle(strip->GetStripEndId());
00272 vendzfit[dplane] = upid.GetZ0();
00273 }
00274 }
00275 break;
00276 default:
00277 break;
00278 }
00279 }
00280 }
00281
00282 // normalize charge weighted fit points, and remove array entries
00283 // with zero pulse height
00284
00285 Int_t iuvtxfit=0;
00286 Int_t ivvtxfit=0;
00287 Int_t iuendfit=0;
00288 Int_t ivendfit=0;
00289
00290 for (Int_t i=0; i<=vtxplanespan; i++) {
00291 if (uvtxphfit[i]>0.) {
00292 uvtxfit[iuvtxfit] = uvtxfit[i]/uvtxphfit[i];
00293 uvtxzfit[iuvtxfit]=uvtxzfit[i];
00294 uvtxphfit[iuvtxfit]=uvtxphfit[i];
00295
00296 iuvtxfit++;
00297 }
00298 if (vvtxphfit[i]>0.) {
00299 vvtxfit[ivvtxfit] = vvtxfit[i]/vvtxphfit[i];
00300 vvtxzfit[ivvtxfit]=vvtxzfit[i];
00301 vvtxphfit[ivvtxfit]=vvtxphfit[i];
00302 ivvtxfit++;
00303 }
00304 if (uendphfit[i]>0.) {
00305 uendfit[iuendfit] = uendfit[i]/uendphfit[i];
00306 uendzfit[iuendfit]=uendzfit[i];
00307 uendphfit[iuendfit]=uendphfit[i];
00308 iuendfit++;
00309 }
00310 if (vendphfit[i]>0.) {
00311 vendfit[ivendfit] = vendfit[i]/vendphfit[i];
00312 vendzfit[ivendfit]=vendzfit[i];
00313 vendphfit[ivendfit]=vendphfit[i];
00314 ivendfit++;
00315 }
00316 }
00317
00318 //perform weighted fit of u, v vs z positions
00319 Double_t uvtxparm[2];
00320 Double_t vvtxparm[2];
00321 Double_t dudz=0.;
00322 Double_t dvdz=0.;
00323 if (iuvtxfit>1) {
00324 LinearFit::Weighted(iuvtxfit,uvtxzfit,uvtxfit,uvtxphfit,uvtxparm);
00325 dudz = uvtxparm[1];
00326 }
00327 if (ivvtxfit>1) {
00328 LinearFit::Weighted(ivvtxfit,vvtxzfit,vvtxfit,vvtxphfit,vvtxparm);
00329 dvdz = vvtxparm[1];
00330 }
00331 Double_t uendparm[2];
00332 Double_t vendparm[2];
00333 if (iuendfit>1) {
00334 LinearFit::Weighted(iuendfit,uendzfit,uendfit,uendphfit,uendparm);
00335
00336 }
00337 if (ivendfit>1) {
00338 LinearFit::Weighted(ivendfit,vendzfit,vendfit,vendphfit,vendparm);
00339
00340 }
00341
00342 // calculate direction cosines from linear fits above
00343 Double_t cosz=1./sqrt(1.+dudz*dudz+dvdz*dvdz);
00344 Double_t cosu=dudz*cosz;
00345 Double_t cosv=dvdz*cosz;
00346
00347 csh.SetDirCosU(cosu);
00348 csh.SetDirCosV(cosv);
00349 csh.SetDirCosZ(cosz);
00350
00351 csh.SetEndDirCosU(cosu);
00352 csh.SetEndDirCosV(cosv);
00353 csh.SetEndDirCosZ(cosz);
00354
00355 // set the vertex planes and z position. The vertex Z position
00356 // is the position of the most upstream strip. This is not
00357 // correct for cosmics!
00358
00359 PlexStripEndId stripid = begstrip->GetStripEndId();
00360 UgliScintPlnHandle planehandle = ugh.GetScintPlnHandle(stripid);
00361 csh.SetVtxPlane(begstrip->GetPlane());
00362 csh.SetVtxZ(planehandle.GetZ0());
00363
00364 stripid = endstrip->GetStripEndId();
00365 planehandle = ugh.GetScintPlnHandle(stripid);
00366 csh.SetEndPlane(endstrip->GetPlane());
00367 csh.SetEndZ(planehandle.GetZ0());
00368
00369 // the vertex time is defined to be the earliest strip begin time in
00370 // the vertex region defined by VtxPlaneSpan
00371 csh.SetVtxT(tvtx);
00372 csh.SetEndT(tend);
00373 SetUV(&csh);
00374
00375 // if this is a cosmic event, base direction on timing
00376 if(isCosmic){
00377 Double_t fitparm[2] = {0,0};
00378 Double_t timefitchi2;
00379 FindTimingDirection(csh,
00380 ac,
00381 fitparm,
00382 timefitchi2);
00383 if(fitparm[1]<0){
00384
00385 MSG("AlgShowerSR",Msg::kDebug) << " swapping vertex " << endl;
00386
00387 Int_t newvtx = csh.GetEndPlane();
00388 Int_t newend = csh.GetVtxPlane();
00389 Double_t newvtxz = csh.GetEndZ();
00390 Double_t newendz = csh.GetVtxZ();
00391 Double_t newvtxt = csh.GetEndT();
00392 Double_t newendt = csh.GetVtxT();
00393
00394 csh.SetVtxZ(newvtxz);
00395 csh.SetEndZ(newendz);
00396 csh.SetVtxPlane(newvtx);
00397 csh.SetEndPlane(newend);
00398 csh.SetVtxT(newvtxt);
00399 csh.SetEndT(newendt);
00400 }
00401 }
00402
00403
00404 // the vertex and end U/V positions are based on fits if the fit was done
00405
00406 csh.SetVtxU(csh.GetU(csh.GetVtxPlane()));
00407 csh.SetVtxV(csh.GetV(csh.GetVtxPlane()));
00408
00409 csh.SetEndU(csh.GetU(csh.GetEndPlane()));
00410 csh.SetEndV(csh.GetV(csh.GetEndPlane()));
00411
00412 Calibrate(&csh);
00413
00414 CandTrackHandle * associatedtrk=0;
00415 csh.CalibrateEnergy(associatedtrk,ac);
00416
00417 delete [] uvtxfit;
00418 delete [] uvtxphfit;
00419 delete [] uvtxzfit;
00420 delete [] vvtxfit;
00421 delete [] vvtxphfit;
00422 delete [] vvtxzfit;
00423
00424 delete [] uendfit;
00425 delete [] uendphfit;
00426 delete [] uendzfit;
00427 delete [] vendfit;
00428 delete [] vendphfit;
00429 delete [] vendzfit;
00430 }
|
|
|
Definition at line 434 of file AlgShowerSR.cxx. References PlexPlaneId::GetAdjoinScint(), CandRecoHandle::GetBegPlane(), CandStripHandle::GetCharge(), CandHandle::GetDaughterIterator(), VldContext::GetDetector(), CandRecoHandle::GetEndPlane(), CandStripHandle::GetNDigit(), PlexPlaneId::GetPlane(), CandStripHandle::GetPlane(), CandStripHandle::GetPlaneView(), UgliGeomHandle::GetScintPlnHandle(), CandStripHandle::GetTPos(), CandShowerHandle::GetU(), CandShowerHandle::GetV(), CandHandle::GetVldContext(), CandShowerHandle::GetZ(), UgliPlnHandle::GetZ0(), UgliScintPlnHandle::IsValid(), PlexPlaneId::IsValid(), max(), min(), MSG, CandShowerHandle::SetU(), and CandShowerHandle::SetV(). Referenced by AlgShowerSS::RunAlg(), and RunAlg(). 00435 {
00436 TIter stripItr(candshower->GetDaughterIterator());
00437 CandStripHandle *firststrip = 0;
00438 firststrip = dynamic_cast<CandStripHandle*>(stripItr());
00439 if (!firststrip) return; // if no strips, do nothing
00440
00441 const VldContext *vldc = firststrip->GetVldContext();
00442 DetectorType::Detector_t det = vldc->GetDetector();
00443
00444 UgliGeomHandle ugh = UgliGeomHandle(*vldc);
00445
00446 CandStripHandleItr orderedstripItr(candshower->GetDaughterIterator());
00447 CandStripHandleKeyFunc *stripKf = orderedstripItr.CreateKeyFunc();
00448 stripKf->SetFun(CandStripHandle::KeyFromPlane);
00449 orderedstripItr.GetSet()->AdoptSortKeyFunc(stripKf);
00450 stripKf = 0;
00451 Bool_t first(1);
00452 Int_t oldplane = -1;
00453 PlaneView::PlaneView_t oldview = PlaneView::kUnknown;
00454 Float_t tpos = 0.;
00455 Float_t ph = 0.;
00456 Int_t idir=1;
00457 Int_t vtxplane = candshower->GetBegPlane();
00458 Int_t endplane = candshower->GetEndPlane();
00459 if (vtxplane>endplane) idir=-1;
00460 Int_t begplane = min(vtxplane,endplane);
00461 endplane = max(vtxplane,endplane);
00462
00463 begplane = -1;
00464 endplane = -1;
00465
00466 // find begin and end planes
00467 while (CandStripHandle *strip =
00468 dynamic_cast<CandStripHandle*>(orderedstripItr())) {
00469 if (strip->GetPlaneView()==PlaneView::kU ||
00470 strip->GetPlaneView()==PlaneView::kV) {
00471 if (begplane<0 || strip->GetPlane()<begplane) {
00472 begplane = strip->GetPlane();
00473 }
00474 if (endplane<0 || strip->GetPlane()>endplane) {
00475 endplane = strip->GetPlane();
00476 }
00477 }
00478 }
00479 Int_t *planelist = new Int_t[endplane+1];
00480 Int_t *stripendlist = new Int_t[endplane+1];
00481 if(begplane>-1 && endplane>-1){
00482
00483 for (int i=0; i<=endplane; i++) {
00484 planelist[i] = 0;
00485 stripendlist[i] = 0;
00486 }
00487
00488 // transverse positions
00489 orderedstripItr.Reset();
00490
00491 while (CandStripHandle *strip =
00492 dynamic_cast<CandStripHandle*>(orderedstripItr())) {
00493 if (strip->GetPlaneView()==PlaneView::kU ||
00494 strip->GetPlaneView()==PlaneView::kV) {
00495 planelist[strip->GetPlane()] = strip->GetPlaneView();
00496 if (strip->GetNDigit(StripEnd::kNegative)) {
00497 stripendlist[strip->GetPlane()] += (1<<StripEnd::kNegative);
00498 }
00499 if (strip->GetNDigit(StripEnd::kPositive)) {
00500 stripendlist[strip->GetPlane()] += (1<<StripEnd::kPositive);
00501 }
00502 if (first || strip->GetPlane()==oldplane) {
00503 if (first) {
00504 first = 0;
00505 oldplane = strip->GetPlane();
00506 oldview = strip->GetPlaneView();
00507 }
00508 Float_t stripph = strip->GetCharge();
00509 tpos += strip->GetTPos()*stripph;
00510 ph += stripph;
00511 }
00512 else {
00513 tpos /= ph;
00514 if (oldview==PlaneView::kU) {
00515 candshower->SetU(oldplane,tpos);
00516 } else if (oldview==PlaneView::kV) {
00517 candshower->SetV(oldplane,tpos);
00518 }
00519 oldplane = strip->GetPlane();
00520 oldview = strip->GetPlaneView();
00521 Float_t stripph = strip->GetCharge();
00522 tpos = strip->GetTPos()*stripph;
00523 ph = stripph;
00524 }
00525 }
00526 }
00527 if (ph>0.) {
00528 tpos /= ph;
00529 if (oldview==PlaneView::kU) {
00530 candshower->SetU(oldplane,tpos);
00531 } else if (oldview==PlaneView::kV) {
00532 candshower->SetV(oldplane,tpos);
00533 }
00534 }
00535
00536 // create a starting and stopping PlexPlaneId
00537 Int_t idirAdjoin = (begplane>endplane) ? -1 : 1; // direction
00538 PlexPlaneId planeid(det,begplane,false);
00539 PlexPlaneId planeidend(det,endplane,false);
00540 PlexPlaneId planeid_toofar = planeidend.GetAdjoinScint(idirAdjoin);
00541
00542 // after each step, if not reached end, move to adjoining *scint* plane
00543 for ( ; planeid != planeid_toofar ;
00544 planeid = planeid.GetAdjoinScint(idirAdjoin) ) {
00545
00546 // quit if hit something meaningless
00547 if ( ! planeid.IsValid() ) break;
00548
00549 UgliScintPlnHandle scintpln = ugh.GetScintPlnHandle(planeid);
00550
00551 if ( ! scintpln.IsValid() ) continue;
00552
00553 Int_t iplane = planeid.GetPlane();
00554
00555 Float_t zpos = scintpln.GetZ0();
00556 for (Int_t planeview=PlaneView::kU; planeview<=PlaneView::kV;
00557 planeview++) {
00558 if (planelist[iplane]!=planeview) {
00559 Int_t found = 0;
00560 Int_t nfound = 0;
00561 Int_t jplane[2];
00562
00563 // search upstream
00564 for (Int_t iplane1=iplane-1; iplane1>=begplane && !found;
00565 iplane1--) {
00566 if (planelist[iplane1]==planeview) {
00567 found++;
00568 jplane[nfound] = iplane1;
00569 nfound++;
00570 }
00571 }
00572 Int_t ndown = 1;
00573 if (!found) {
00574 ndown++;
00575 }
00576 found = 0;
00577
00578 // search downstream
00579 for (Int_t iplane1=iplane+1; iplane1<=endplane && found<ndown;
00580 iplane1++) {
00581 if (planelist[iplane1]==planeview) {
00582 found++;
00583 jplane[nfound] = iplane1;
00584 nfound++;
00585 }
00586 }
00587 if (!found) {
00588 for (Int_t iplane1=jplane[0]-1; iplane1>=begplane && !found;
00589 iplane1--) {
00590 if (planelist[iplane1]==planeview) {
00591 found++;
00592 jplane[nfound] = iplane1;
00593 nfound++;
00594 }
00595 }
00596 }
00597 if (nfound==1) {
00598 if (planeview==PlaneView::kU) {
00599 candshower->SetU(iplane,candshower->GetU(jplane[0]));
00600 } else {
00601 candshower->SetV(iplane,candshower->GetV(jplane[0]));
00602 }
00603 }
00604 else {
00605 Float_t z[2];
00606 z[0] = candshower->GetZ(jplane[0]);
00607 z[1] = candshower->GetZ(jplane[1]);
00608 Float_t x[2];
00609 if (planeview==PlaneView::kU) {
00610 x[0] = candshower->GetU(jplane[0]);
00611 x[1] = candshower->GetU(jplane[1]);
00612 Float_t denom = (z[1]-z[0]);
00613 if (denom) candshower->SetU(iplane,
00614 x[0] + (zpos-z[0]) * ((x[1]-x[0])/denom));
00615 else {
00616 MSG("Shower",Msg::kWarning) << endl
00617 << "Denominator (z[1]-z[0]) is zero."
00618 << " SetU not called." << endl;
00619 }
00620 } else {
00621 x[0] = candshower->GetV(jplane[0]);
00622 x[1] = candshower->GetV(jplane[1]);
00623 Float_t denom = (z[1]-z[0]);
00624 if (denom) candshower->SetV(iplane,
00625 x[0] + (zpos-z[0]) * ((x[1]-x[0])/denom));
00626 else {
00627 MSG("Shower",Msg::kWarning) << endl
00628 << "Denominator is (z[1]-z[0]) zero."
00629 << " SetV not called." << endl;
00630 }
00631 }
00632 }
00633 }
00634 }
00635 }
00636 }
00637 delete [] planelist;
00638 delete [] stripendlist;
00639
00640 }
|
|
|
Reimplemented from AlgBase. Reimplemented in AlgShowerSS. Definition at line 865 of file AlgShowerSR.cxx. 00866 {
00867 }
|
1.3.9.1