00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00012
00013 #include "TMath.h"
00014
00015 #include <cassert>
00016 #include <cmath>
00017 #include <iostream>
00018
00019 #include "MessageService/MsgService.h"
00020 #include "RecoBase/CandClusterHandle.h"
00021 #include "RecoBase/CandSliceHandle.h"
00022 #include "RecoBase/CandShowerHandle.h"
00023 #include "RecoBase/CandTrackHandle.h"
00024 #include "RecoBase/CandFitTrackHandle.h"
00025 #include "RecoBase/CandShower.h"
00026 #include "Navigation/NavKey.h"
00027 #include "Navigation/NavSet.h"
00028 #include "Validity/VldContext.h"
00029 #include "Algorithm/AlgConfig.h"
00030 #include "UgliGeometry/UgliGeomHandle.h"
00031 #include "UgliGeometry/UgliScintPlnHandle.h"
00032 #include "DataUtil/PlaneOutline.h"
00033 #include "DataUtil/EnergyCorrections.h"
00034
00035 ClassImp(CandShowerHandle)
00036
00037
00038 CVSID("$Id: CandShowerHandle.cxx,v 1.52 2008/11/05 17:33:15 rodriges Exp $");
00039
00040
00041 CandShowerHandle::CandShowerHandle()
00042 {
00043 }
00044
00045
00046 CandShowerHandle::CandShowerHandle(const CandShowerHandle &cdh) :
00047 CandRecoHandle(cdh)
00048 {
00049 }
00050
00051
00052 CandShowerHandle::CandShowerHandle(CandShower *cd) :
00053 CandRecoHandle(cd)
00054 {
00055 }
00056
00057
00058 CandShowerHandle::~CandShowerHandle()
00059 {
00060 }
00061
00062
00063 CandShowerHandle *CandShowerHandle::DupHandle() const
00064 {
00065 return (new CandShowerHandle(*this));
00066 }
00067
00068
00069 void CandShowerHandle::Trace(const char *c) const
00070 {
00071 MSG("Cand", Msg::kDebug)
00072 << "**********Begin CandShowerHandle::Trace(\"" << c << "\")" << endl
00073 << "Information from CandShowerHandle's CandHandle: " << endl;
00074 CandHandle::Trace(c);
00075 MSG("Cand", Msg::kDebug)
00076 << "**********End CandShowerHandle::Trace(\"" << c << "\")" << endl;
00077 }
00078
00079
00080
00081
00082
00083
00084
00085 void CandShowerHandle::SetU(Int_t plane, Float_t tpos)
00086 {
00087 CandShower *shower = dynamic_cast<CandShower*>(GetOwnedCandBase());
00088 shower->fUPos[plane] = tpos;
00089 }
00090
00091 Float_t CandShowerHandle::GetU(Int_t plane) const
00092 {
00093 const CandShower *shower = dynamic_cast<const CandShower*>(GetCandBase());
00094 if ((shower->fUPos).count(plane)) return shower->fUPos[plane];
00095 return -99999.;
00096 }
00097
00098
00099
00100 void CandShowerHandle::SetV(Int_t plane, Float_t tpos)
00101 {
00102 CandShower *shower = dynamic_cast<CandShower*>(GetOwnedCandBase());
00103 shower->fVPos[plane] = tpos;
00104 }
00105
00106 Float_t CandShowerHandle::GetV(Int_t plane) const
00107 {
00108 const CandShower *shower = dynamic_cast<const CandShower*>(GetCandBase());
00109 if ((shower->fVPos).count(plane)) return shower->fVPos[plane];
00110 return -99999.;
00111 }
00112
00113
00114
00115
00116 void CandShowerHandle::SetMinStripPE(Double_t minstrippe)
00117 {
00118 CandShower *shower = dynamic_cast<CandShower*>(GetOwnedCandBase());
00119 shower->fMinStripPE=minstrippe;
00120 }
00121
00122 Double_t CandShowerHandle::GetMinStripPE() const
00123 {
00124 const CandShower *shower = dynamic_cast<const CandShower*>(GetCandBase());
00125 return shower->fMinStripPE;
00126 }
00127
00128
00129
00130 Float_t CandShowerHandle::GetZ(Int_t plane) const
00131 {
00132 TIter stripItr(GetDaughterIterator());
00133 while (CandStripHandle *strip =
00134 dynamic_cast<CandStripHandle*>(stripItr())) {
00135 if (strip->GetPlane()==plane) return strip->GetZPos();
00136 }
00137 return -1.;
00138 }
00139
00140
00141
00142 void CandShowerHandle::SetT(Int_t plane, StripEnd::StripEnd_t stripend_t, Double_t time)
00143 {
00144 CandShower *shower = dynamic_cast<CandShower*>(GetOwnedCandBase());
00145 switch (stripend_t) {
00146 case StripEnd::kNegative:
00147 shower->fTime[0][plane] = time;
00148 break;
00149 case StripEnd::kPositive:
00150 shower->fTime[1][plane] = time;
00151 break;
00152 default:
00153 shower->fTime[0][plane] = time;
00154 break;
00155 }
00156 }
00157
00158
00159
00160 void CandShowerHandle::ClearUVT()
00161 {
00162 CandShower *shower = dynamic_cast<CandShower*>(GetOwnedCandBase());
00163 shower->fUPos.clear();
00164 shower->fVPos.clear();
00165 shower->fTime[0].clear();
00166 shower->fTime[1].clear();
00167 }
00168
00169
00170
00171 Float_t CandShowerHandle::GetMinU(Int_t iplane, Double_t minPE) const{
00172 CandStripHandleItr sItr(GetDaughterIterator());
00173 CandStripHandle * begstrip = sItr();
00174 if(!begstrip)return -999;
00175 const VldContext * vld = begstrip->GetVldContext();
00176 if(!vld)return -999;
00177 PlexPlaneId plnid(vld->GetDetector(),iplane,false);
00178 if(plnid.GetPlaneView()!=PlaneView::kU)return -999.;
00179 CandStripHandleItr stripItr(GetDaughterIterator());
00180 CandStripHandleKeyFunc *stripKf = stripItr.CreateKeyFunc();
00181 stripKf->SetFun(CandStripHandle::KeyFromPlane);
00182 stripItr.GetSet()->AdoptSortKeyFunc(stripKf);
00183 stripKf = 0;
00184 stripItr.GetSet()->Slice(iplane);
00185
00186 Float_t minU=999.;
00187 while (const CandStripHandle *strip =
00188 dynamic_cast<const CandStripHandle*>(stripItr())) {
00189
00190 if(iplane<GetBegPlane() || iplane > GetEndPlane()) return 0.;
00191
00192 if(strip->GetTPos() < minU && strip->GetCharge(CalDigitType::kPE) > minPE )
00193 minU=strip->GetTPos();
00194 }
00195 if(minU==999)minU=0;
00196 return minU;
00197 }
00198
00199
00200 Float_t CandShowerHandle::GetMinV(Int_t iplane, Double_t minPE) const{
00201 CandStripHandleItr sItr(GetDaughterIterator());
00202 CandStripHandle * begstrip = sItr();
00203 if(!begstrip)return -999;
00204 const VldContext * vld = begstrip->GetVldContext();
00205 if(!vld)return -999;
00206 PlexPlaneId plnid(vld->GetDetector(),iplane,false);
00207 if(plnid.GetPlaneView()!=PlaneView::kV)return -999.;
00208 if(iplane<GetBegPlane() || iplane > GetEndPlane()) return 0.;
00209 CandStripHandleItr stripItr(GetDaughterIterator());
00210 CandStripHandleKeyFunc *stripKf = stripItr.CreateKeyFunc();
00211 stripKf->SetFun(CandStripHandle::KeyFromPlane);
00212 stripItr.GetSet()->AdoptSortKeyFunc(stripKf);
00213 stripKf = 0;
00214 stripItr.GetSet()->Slice(iplane);
00215
00216 Float_t minV=999.;
00217 while (const CandStripHandle *strip =
00218 dynamic_cast<const CandStripHandle*>(stripItr())) {
00219 if(strip->GetTPos()<minV && strip->GetCharge(CalDigitType::kPE) > minPE )
00220 minV=strip->GetTPos();
00221 }
00222 if(minV==999.)minV=0;
00223 return minV;
00224 }
00225
00226
00227
00228 Float_t CandShowerHandle::GetMaxU(Int_t iplane, Double_t minPE) const{
00229 CandStripHandleItr sItr(GetDaughterIterator());
00230 CandStripHandle * begstrip = sItr();
00231 if(!begstrip)return 999;
00232 const VldContext * vld = begstrip->GetVldContext();
00233 if(!vld)return 999;
00234 PlexPlaneId plnid(vld->GetDetector(),iplane,false);
00235 if(plnid.GetPlaneView()!=PlaneView::kU)return 999.;
00236 if(iplane<GetBegPlane() || iplane > GetEndPlane()) return 0.;
00237
00238 CandStripHandleItr stripItr(GetDaughterIterator());
00239 CandStripHandleKeyFunc *stripKf = stripItr.CreateKeyFunc();
00240 stripKf->SetFun(CandStripHandle::KeyFromPlane);
00241 stripItr.GetSet()->AdoptSortKeyFunc(stripKf);
00242 stripKf = 0;
00243 stripItr.GetSet()->Slice(iplane);
00244
00245 Float_t maxU=-999.;
00246 while (const CandStripHandle *strip =
00247 dynamic_cast<const CandStripHandle*>(stripItr())) {
00248 if(strip->GetTPos() > maxU&& strip->GetCharge(CalDigitType::kPE) > minPE ) maxU=strip->GetTPos();
00249 }
00250 if(maxU==-999.)maxU=0;
00251 return maxU;
00252 }
00253
00254
00255
00256 Float_t CandShowerHandle::GetMaxV(Int_t iplane, Double_t minPE) const {
00257 CandStripHandleItr sItr(GetDaughterIterator());
00258 CandStripHandle * begstrip = sItr();
00259 if(!begstrip)return 999;
00260 const VldContext * vld = begstrip->GetVldContext();
00261 if(!vld)return 999;
00262 PlexPlaneId plnid(vld->GetDetector(),iplane,false);
00263 if(plnid.GetPlaneView()!=PlaneView::kV)return 999.;
00264 if(iplane<GetBegPlane() || iplane > GetEndPlane()) return 0.;
00265
00266 CandStripHandleItr stripItr(GetDaughterIterator());
00267 CandStripHandleKeyFunc *stripKf = stripItr.CreateKeyFunc();
00268 stripKf->SetFun(CandStripHandle::KeyFromPlane);
00269 stripItr.GetSet()->AdoptSortKeyFunc(stripKf);
00270 stripKf = 0;
00271 stripItr.GetSet()->Slice(iplane);
00272 Float_t maxV=-999.;
00273 while (const CandStripHandle *strip =
00274 dynamic_cast<const CandStripHandle*>(stripItr())) {
00275 if(strip->GetTPos()>maxV && strip->GetCharge(CalDigitType::kPE) > minPE)
00276 maxV=strip->GetTPos();
00277 }
00278 if(maxV==-999)maxV=0;
00279 return maxV;
00280 }
00281
00282
00283 Int_t CandShowerHandle::GetNStrips(Int_t iplane){
00284 Int_t nstrips=0;
00285 CandStripHandleItr stripItr(GetDaughterIterator());
00286 while (const CandStripHandle *strip =
00287 dynamic_cast<const CandStripHandle*>(stripItr())) {
00288 if(strip->GetPlane()==iplane)nstrips++;
00289 }
00290 return nstrips;
00291 }
00292
00293
00294
00295 Double_t CandShowerHandle::GetT(Int_t plane,StripEnd::StripEnd_t stripend_t) const
00296 {
00297 const CandShower *shower = dynamic_cast<const CandShower*>(GetCandBase());
00298 if (stripend_t==StripEnd::kNegative) {
00299 if ((shower->fTime[0]).count(plane)) {
00300 return shower->fTime[0][plane];
00301 }
00302 return -99999.;
00303 }
00304 if (stripend_t==StripEnd::kPositive) {
00305 if ((shower->fTime[1]).count(plane)) {
00306 return shower->fTime[1][plane];
00307 }
00308 return -99999.;
00309 }
00310 if ((shower->fTime[0]).count(plane) && (shower->fTime[1]).count(plane)) {
00311 return min(shower->fTime[0][plane],shower->fTime[1][plane]);
00312 }
00313 else if ((shower->fTime[0]).count(plane)) {
00314 return shower->fTime[0][plane];
00315 }
00316 else if ((shower->fTime[1]).count(plane)) {
00317 return shower->fTime[1][plane];
00318 }
00319 return -99999.;
00320 }
00321
00322 Double_t CandShowerHandle::GetT(StripEnd::StripEnd_t stripend_t,Int_t plane) const
00323 {
00324 return this->GetT(plane,stripend_t);
00325 }
00326
00327 Double_t CandShowerHandle::GetT(Int_t plane) const
00328 {
00329 return this->GetT(plane,StripEnd::kWhole);
00330 }
00331
00332
00333 Bool_t CandShowerHandle::IsTPosValid(Int_t plane) const
00334 {
00335 const CandShower *shower = dynamic_cast<const CandShower*>(GetCandBase());
00336 if ((shower->fUPos).count(plane) && (shower->fVPos).count(plane)) {
00337 return kTRUE;
00338 }
00339 return kFALSE;
00340 }
00341
00342 Bool_t CandShowerHandle::BelongsWithTrack(CandTrackHandle * trk,
00343 AlgConfig & ac,
00344 const VldContext * vldcptr,
00345 Double_t tolTPos2, Double_t tolZPos, Double_t tolTime){
00346
00347 if(!trk)return false;
00348
00349 Int_t pSMPlaneLast = ac.GetInt("SMPlaneLast");
00350 Int_t pSMPlaneFirst = ac.GetInt("SMPlaneFirst");
00351 VldContext vldc = *vldcptr;
00352 UgliGeomHandle ugh(vldc);
00353 Double_t zGapSM=0;
00354
00355
00356
00357
00358
00359 if(vldc.GetDetector() == Detector::kFar){
00360
00361 PlexPlaneId scintlastid(vldc.GetDetector(),pSMPlaneLast,kFALSE);
00362 PlexPlaneId scintfirstid(vldc.GetDetector(),pSMPlaneFirst,kFALSE);
00363 UgliScintPlnHandle scintlast = ugh.GetScintPlnHandle(scintlastid);
00364 UgliScintPlnHandle scintfirst = ugh.GetScintPlnHandle(scintfirstid);
00365 if (scintlast.IsValid() && scintfirst.IsValid()) {
00366 zGapSM=scintfirst.GetZ0()-scintlast.GetZ0()-0.0594;
00367 }
00368 }
00369
00370 MSG("RecoBase",Msg::kDebug)
00371 << " comparing shower at "
00372 << this->GetVtxPlane()
00373 << " " << this->GetVtxU()
00374 << " " << this->GetVtxV()
00375 << " with track at " << trk->GetVtxPlane()
00376 << " " << trk->GetVtxU()
00377 << " " << trk->GetVtxV() << endl;
00378 Float_t tolTPos = TMath::Sqrt(tolTPos2);
00379 Int_t fwdTrkPlane=min(trk->GetVtxPlane(),trk->GetEndPlane());
00380 Int_t bckTrkPlane=max(trk->GetVtxPlane(),trk->GetEndPlane());
00381 Int_t fwdShwPlane=min(this->GetVtxPlane(),this->GetEndPlane());
00382 Int_t bckShwPlane=max(this->GetVtxPlane(),this->GetEndPlane());
00383
00384 Double_t dt = trk->GetVtxT()-this->GetVtxT();
00385
00386
00387
00388
00389 if( bckShwPlane>=fwdTrkPlane && fwdShwPlane<=bckTrkPlane && fabs(dt)<tolTime){
00390 MSG("RecoBase",Msg::kDebug) << " trk and shower overlap in Z and time " << endl;
00391 Bool_t matchu=false;
00392 Bool_t matchv=false;
00393 for(Int_t iloop=0;iloop<2;iloop++){
00394 if(iloop >0 && (matchu || matchv))tolTPos=tolTPos*2;
00395
00396 if(iloop >0 && !matchu && !matchv) break;
00397 for (Int_t iplane=fwdShwPlane; iplane<=bckShwPlane;iplane++){
00398
00399 Double_t trkU(0.),trkV(0.);
00400 PlexPlaneId plnid(GetVldContext()->GetDetector(),iplane,false);
00401 if(plnid.GetPlaneView()==PlaneView::kU){
00402 trkU=trk->GetU(iplane);
00403 if(!trk->IsTPosValid(iplane)){
00404 if(abs(iplane-trk->GetVtxPlane())<abs(iplane-trk->GetEndPlane())){
00405 UgliScintPlnHandle scintpln = ugh.GetScintPlnHandle(plnid);
00406 Double_t dz=scintpln.GetZ0()-trk->GetVtxZ();
00407 trkU = trk->GetVtxU() + dz*trk->GetVtxDirCosU()/trk->GetVtxDirCosZ();
00408 }
00409 else{
00410 UgliScintPlnHandle scintpln = ugh.GetScintPlnHandle(plnid);
00411 Double_t dz=scintpln.GetZ0()-trk->GetEndZ();
00412 trkU = (trk->GetEndU() + dz*trk->GetEndDirCosU()/trk->GetEndDirCosZ());
00413 }
00414 }
00415 if(trkU>=this->GetMinU(iplane)-tolTPos && trkU<=this->GetMaxU(iplane)+tolTPos && this->GetNStrips(iplane)>0){
00416 MSG("RecoBase", Msg::kDebug)<< " u match! (details follow)" << endl;
00417 matchu=true;
00418 }
00419 }
00420 else if(plnid.GetPlaneView()==PlaneView::kV){
00421 trkV=trk->GetV(iplane);
00422 if(!trk->IsTPosValid(iplane)){
00423 if(abs(iplane-trk->GetVtxPlane())<abs(iplane-trk->GetEndPlane())){
00424 UgliScintPlnHandle scintpln = ugh.GetScintPlnHandle(plnid);
00425 Double_t dz=scintpln.GetZ0()-trk->GetVtxZ();
00426 trkV = (trk->GetVtxV() + dz*trk->GetDirCosV()/trk->GetDirCosZ());
00427 }
00428 else{
00429 UgliScintPlnHandle scintpln = ugh.GetScintPlnHandle(plnid);
00430 Double_t dz=scintpln.GetZ0()-trk->GetEndZ();
00431 trkV= (trk->GetEndV() + dz*trk->GetEndDirCosV()/trk->GetEndDirCosZ());
00432 }
00433 }
00434 if(trkV>=this->GetMinV(iplane)-tolTPos && trkV<=this->GetMaxV(iplane)+tolTPos && this->GetNStrips(iplane)>0){
00435 MSG("RecoBase", Msg::kDebug)<< " v match! (details follow)" << endl;
00436 matchv=true;
00437 }
00438 }
00439 MSG("RecoBase",Msg::kDebug) << " plane " << iplane
00440 << " trk u " << trkU
00441 << " min/max U " << this->GetMinU(iplane)
00442 << "/" << this->GetMaxU(iplane)
00443 << " trk v " << trkV
00444 << " min/max V " << this->GetMinV(iplane)
00445 << "/" << this->GetMaxV(iplane) << endl;
00446 if(matchu && matchv) {
00447 MSG("RecoBase", Msg::kDebug)<< " 3D match! " << endl;
00448 return true;
00449 }
00450 }
00451 }
00452 }
00453 if( this->GetVtxZ()>min(trk->GetVtxZ(),trk->GetEndZ())-tolZPos &&
00454 this->GetVtxZ()<max(trk->GetVtxZ(),trk->GetEndZ())+tolZPos) {
00455 Double_t du= trk->GetVtxU()-this->GetVtxU();
00456 Double_t dv= trk->GetVtxV()-this->GetVtxV();
00457 if(trk->IsTPosValid(this->GetVtxPlane())){
00458 MSG("RecoBase",Msg::kDebug) << " TPos is valid @ shower vtx "
00459 << " track u/v " << trk->GetU(this->GetVtxPlane())
00460 << " " << trk->GetV(this->GetVtxPlane()) << endl;
00461
00462 du = this->GetVtxU()-trk->GetU(this->GetVtxPlane());
00463 dv = this->GetVtxV()-trk->GetV(this->GetVtxPlane());
00464 }
00465 MSG("RecoBase",Msg::kDebug)
00466 << " at plane " << this->GetVtxPlane() << " dt2 "
00467 << du*du+dv*dv << "/" << tolTPos2
00468 << " dt " << dt*1.e9
00469 << "/" << tolTime*1e9 << "\n";
00470 if(dt<tolTime &&
00471 du*du+dv*dv<tolTPos2) return true;
00472 }
00473
00474 Double_t trkZ=trk->GetVtxZ();
00475 Double_t trkU=trk->GetVtxU();
00476 Double_t trkV=trk->GetVtxV();
00477 Double_t trkT=trk->GetVtxT();
00478 Double_t trkDirU=trk->GetVtxDirCosU();
00479 Double_t trkDirV=trk->GetVtxDirCosV();
00480 Double_t trkDirZ=trk->GetVtxDirCosZ();
00481 Int_t trkPlane=trk->GetVtxPlane();
00482 if(fabs(this->GetVtxZ()-trk->GetEndZ())<fabs(this->GetVtxZ()-trk->GetVtxZ())){
00483 trkZ=trk->GetEndZ();
00484 trkU=trk->GetEndU();
00485 trkV=trk->GetEndV();
00486 trkT=trk->GetEndT();
00487 trkPlane=trk->GetEndPlane();
00488 trkDirU=trk->GetEndDirCosU();
00489 trkDirV=trk->GetEndDirCosV();
00490 trkDirZ=trk->GetEndDirCosZ();
00491 }
00492 Double_t dz = this->GetVtxZ()-trkZ;
00493 dt = this->GetVtxT()-trkT;
00494
00495 if (vldcptr->GetDetector()==Detector::kFar &&
00496 this->GetVtxPlane()<=pSMPlaneLast &&
00497 trkPlane>=pSMPlaneFirst) dz+=zGapSM;
00498 else if (vldcptr->GetDetector()==Detector::kFar &&
00499 this->GetVtxPlane()>=pSMPlaneLast &&
00500 trkPlane<=pSMPlaneFirst) dz-=zGapSM;
00501
00502 Double_t du = (trkU + dz*trkDirU/trkDirZ) - this->GetVtxU();
00503 Double_t dv = (trkV + dz*trkDirV/trkDirZ) - this->GetVtxV();
00504
00505 MSG("RecoBase",Msg::kDebug)
00506 << " dvertex shower/track " << du
00507 << " " << dv << " " << dz <<" " << dt*1.e9 << "\n";
00508 if (du*du+dv*dv<tolTPos2 &&
00509 fabs(dz)<tolZPos &&
00510 fabs(dt)<tolTime) return true;
00511
00512 dz = this->GetEndZ()-trkZ;
00513 dt = this->GetVtxT()-trkT;
00514
00515 if (vldcptr->GetDetector()==Detector::kFar &&
00516 this->GetVtxPlane()<=pSMPlaneLast &&
00517 trkPlane>=pSMPlaneFirst) dz+=zGapSM;
00518 else if (vldcptr->GetDetector()==Detector::kFar &&
00519 this->GetVtxPlane()>=pSMPlaneLast &&
00520 trkPlane<=pSMPlaneFirst) dz-=zGapSM;
00521
00522 du = (trkU + dz*trkDirU/trkDirZ) - this->GetEndU();
00523 dv = (trkV + dz*trkDirV/trkDirZ) - this->GetEndV();
00524
00525 MSG("RecoBase",Msg::kDebug)
00526 << " dvertex shower/track " << du
00527 << " " << dv << " " << dz <<" " << dt*1.e9 << "\n";
00528 if (du*du+dv*dv<tolTPos2 &&
00529 fabs(dz)<tolZPos &&
00530 fabs(dt)<tolTime) return true;
00531
00532 return false;
00533 }
00534
00535 Bool_t CandShowerHandle::BelongsWithShower(CandShowerHandle * shw,
00536 AlgConfig & ac,
00537 const VldContext * vldcptr,
00538 Double_t tolTPos2, Double_t tolZPos, Double_t tolTime){
00539
00540 if(!shw)return false;
00541
00542 Int_t pSMPlaneLast = ac.GetInt("SMPlaneLast");
00543 Int_t pSMPlaneFirst = ac.GetInt("SMPlaneFirst");
00544 VldContext vldc = *vldcptr;
00545 UgliGeomHandle ugh(vldc);
00546 Double_t zGapSM=0;
00547
00548
00549
00550
00551
00552
00553 if(vldc.GetDetector() == Detector::kFar){
00554
00555 PlexPlaneId scintlastid(vldc.GetDetector(),pSMPlaneLast,kFALSE);
00556 PlexPlaneId scintfirstid(vldc.GetDetector(),pSMPlaneFirst,kFALSE);
00557 UgliScintPlnHandle scintlast = ugh.GetScintPlnHandle(scintlastid);
00558 UgliScintPlnHandle scintfirst = ugh.GetScintPlnHandle(scintfirstid);
00559 if (scintlast.IsValid() && scintfirst.IsValid()) {
00560 zGapSM=scintfirst.GetZ0()-scintlast.GetZ0()-0.0594;
00561 }
00562 }
00563
00564 MSG("RecoBase",Msg::kDebug) << " shower extents " << this->GetVtxZ() << " " << this->GetEndZ() << " " << shw->GetVtxZ() << " " << shw->GetEndZ() << endl;
00565 Double_t dz = this->GetVtxZ()-shw->GetVtxZ();
00566 Double_t dzend= this->GetEndZ()-shw->GetVtxZ();
00567 Double_t dzend2= this->GetVtxZ()-shw->GetEndZ();
00568 Double_t dzend3= this->GetEndZ()-shw->GetEndZ();
00569 Double_t du= this->GetVtxU()-shw->GetVtxU();
00570 Double_t dv= this->GetVtxV()-shw->GetVtxV();
00571 Double_t dt= this->GetVtxT()-shw->GetVtxT();
00572
00573
00574 if (vldcptr->GetDetector()==Detector::kFar &&
00575 this->GetVtxPlane()<=pSMPlaneLast &&
00576 shw->GetVtxPlane()>=pSMPlaneFirst) dz+=zGapSM;
00577 else if (vldcptr->GetDetector()==Detector::kFar &&
00578 this->GetVtxPlane()>=pSMPlaneLast &&
00579 shw->GetVtxPlane()<=pSMPlaneFirst) dz-=zGapSM;
00580
00581 if (vldcptr->GetDetector()==Detector::kFar &&
00582 this->GetEndPlane()<=pSMPlaneLast &&
00583 shw->GetVtxPlane()>=pSMPlaneFirst) dzend+=zGapSM;
00584 else if (vldcptr->GetDetector()==Detector::kFar &&
00585 this->GetEndPlane()>=pSMPlaneLast &&
00586 shw->GetVtxPlane()<=pSMPlaneFirst) dzend-=zGapSM;
00587 if(fabs(dz)>fabs(dzend)){
00588 du= this->GetEndU()-shw->GetVtxU();
00589 dv= this->GetEndV()-shw->GetVtxV();
00590 dz=dzend;
00591 }
00592 if (vldcptr->GetDetector()==Detector::kFar &&
00593 this->GetVtxPlane()<=pSMPlaneLast &&
00594 shw->GetEndPlane()>=pSMPlaneFirst) dzend2+=zGapSM;
00595 else if (vldcptr->GetDetector()==Detector::kFar &&
00596 this->GetVtxPlane()>=pSMPlaneLast &&
00597 shw->GetEndPlane()<=pSMPlaneFirst) dzend2-=zGapSM;
00598 if(fabs(dz)>fabs(dzend2)){
00599 du= this->GetVtxU()-shw->GetEndU();
00600 dv= this->GetVtxV()-shw->GetEndV();
00601 dz=dzend2;
00602 }
00603 if (vldcptr->GetDetector()==Detector::kFar &&
00604 this->GetEndPlane()<=pSMPlaneLast &&
00605 shw->GetEndPlane()>=pSMPlaneFirst) dzend3+=zGapSM;
00606 else if (vldcptr->GetDetector()==Detector::kFar &&
00607 this->GetEndPlane()>=pSMPlaneLast &&
00608 shw->GetEndPlane()<=pSMPlaneFirst) dzend3-=zGapSM;
00609 if(fabs(dz)>fabs(dzend3)){
00610 du= this->GetEndU()-shw->GetEndU();
00611 dv= this->GetEndV()-shw->GetEndV();
00612 dz=dzend3;
00613 }
00614
00615 Double_t tolTp=tolTPos2;
00616 Double_t tolZ=tolZPos;
00617 if(this->GetEnergy()>15.0 || shw->GetEnergy()>15.0){
00618 tolTp=tolTPos2*4;
00619 }
00620 MSG("RecoBase",Msg::kDebug)
00621 << " dvertex shower/shower " << du
00622 << " " << dv << " " << dz <<" " << dt*1.e9 << "\n";
00623 if(( (du*du+dv*dv<tolTp &&fabs(dz)<tolZ) ||
00624 (du*du<tolTp/4. && dv*dv<tolTp*4. && fabs(dz)<tolZ/2.) ||
00625 (du*du<tolTp*4 && dv*dv<tolTp/4. && fabs(dz)<tolZ/2.))
00626 && fabs(dt)<tolTime) return true;
00627
00628 return false;
00629 }
00630
00631
00632 void CandShowerHandle::AddCluster(CandClusterHandle *cluster)
00633 {
00634 const TObjArray &clusterlist =
00635 (dynamic_cast<CandShower*>(GetOwnedCandBase()))->fClusterList;
00636 Bool_t found(0);
00637 for (Int_t i=0; i<=clusterlist.GetLast() && !found; i++) {
00638 CandClusterHandle *target =
00639 dynamic_cast<CandClusterHandle*>(clusterlist.At(i));
00640 if (*cluster == *target) found = 1;
00641 }
00642 if (!found) {
00643 CandClusterHandle * cl=cluster->DupHandle();
00644 (dynamic_cast<CandShower*>(GetOwnedCandBase()))->fClusterList.
00645 Add(cl);
00646 }
00647 return;
00648 }
00649
00650 void CandShowerHandle::RemoveCluster(CandClusterHandle *cluster)
00651 {
00652 const TObjArray &clusterlist =
00653 (dynamic_cast<CandShower*>(GetOwnedCandBase()))->fClusterList;
00654 Bool_t found(0);
00655 for (Int_t i=0; i<=clusterlist.GetLast() && !found; i++) {
00656 CandClusterHandle *target =
00657 dynamic_cast<CandClusterHandle*>(clusterlist.At(i));
00658 if (*cluster == *target){
00659 (dynamic_cast<CandShower*>(GetOwnedCandBase()))->fClusterList.
00660 RemoveAt(i);
00661 delete target;
00662 (dynamic_cast<CandShower*>(GetOwnedCandBase()))->fClusterList.
00663 Compress();
00664 return;
00665 }
00666 }
00667 return;
00668 }
00669
00670
00671 bool CandShowerHandle::IsContained(){
00672
00673
00674 CandStripHandleItr sItr(GetDaughterIterator());
00675 CandStripHandle * begstrip = sItr();
00676 if(!begstrip)return true;
00677 const VldContext * vld = begstrip->GetVldContext();
00678 if(!vld)return true;
00679
00680 Bool_t contained =true;
00681 double totcharge = 0;
00682 double containedcharge = 0;
00683 UgliGeomHandle ugh(*vld);
00684 PlaneOutline pl;
00685 float detzmin=0;
00686 float detzmax=999;
00687 ugh.GetZExtent(detzmin,detzmax,-1);
00688 float u=0,v=0;
00689 float xedge,yedge,dist;
00690
00691 while(CandStripHandle * strip = sItr()){
00692 float z = strip->GetZPos();
00693 if(z<detzmin+0.1*Munits::m ||
00694 z>detzmax-0.1*Munits::m) contained=false;
00695 PlexPlaneId plnid(vld->GetDetector(),strip->GetPlane(),false);
00696 if(plnid.GetPlaneView()==PlaneView::kV){
00697 v=strip->GetTPos();
00698 u=GetU(strip->GetPlane());
00699 }
00700 else if(plnid.GetPlaneView()==PlaneView::kU){
00701 u=strip->GetTPos();
00702 v=GetV(strip->GetPlane());
00703 }
00704 float x = 0.707*(u-v);
00705 float y = 0.707*(u+v);
00706 pl.DistanceToEdge(x, y,
00707 plnid.GetPlaneView(),
00708 plnid.GetPlaneCoverage(),
00709 dist, xedge, yedge);
00710 bool isInside = pl.IsInside( x, y,
00711 plnid.GetPlaneView(),
00712 plnid.GetPlaneCoverage());
00713
00714 totcharge += strip->GetCharge();
00715 isInside &= dist>0.1*Munits::m;
00716 if(isInside) {
00717 containedcharge +=strip->GetCharge();
00718 }
00719 }
00720 if(totcharge>0) contained = containedcharge/totcharge>0.9;
00721 return contained;
00722 }
00723
00724
00725
00726 const CandClusterHandle *CandShowerHandle::GetCluster(Int_t i) const
00727 {
00728 const TObjArray *fClusterList = &(dynamic_cast<const CandShower*>
00729 (GetCandBase())->fClusterList);
00730 if (i>fClusterList->GetLast()) {
00731 return 0;
00732 }
00733 return dynamic_cast<const CandClusterHandle*>(fClusterList->At(i));
00734 }
00735
00736
00737
00738 Int_t CandShowerHandle::GetLastCluster() const
00739 {
00740 return dynamic_cast<const CandShower*>(GetCandBase())->fClusterList.
00741 GetLast();
00742 }
00743
00744
00745
00746 Bool_t CandShowerHandle::IsUnphysical(Float_t xtalkFrac,Float_t xtalkCut)
00747 {
00748 if(this->GetNStrip()<=0) return true;
00749 Float_t nxtalk = 0;
00750 CandStripHandleItr stripItr(GetDaughterIterator());
00751 while (const CandStripHandle *strip =
00752 dynamic_cast<const CandStripHandle*>(stripItr())) {
00753 if(strip->GetCharge(CalDigitType::kPE) < xtalkCut) nxtalk+=1;
00754 }
00755 if(nxtalk/Float_t(this->GetNStrip())>xtalkFrac) return true;
00756 return false;
00757 }
00758
00759
00760
00761 void CandShowerHandle::SetEnergy(Double_t energy,
00762 CandShowerHandle::ShowerType_t showertype)
00763 {
00764
00765 switch (showertype){
00766 case kWtCC:
00767 dynamic_cast<CandShower*>(GetOwnedCandBase())->fEnergy = energy;
00768 dynamic_cast<CandShower*>(GetOwnedCandBase())->fEnergy_wtCC = energy;
00769 break;
00770 case kCC:
00771 dynamic_cast<CandShower*>(GetOwnedCandBase())->fEnergy_CC = energy;
00772 break;
00773 case kWtNC:
00774 dynamic_cast<CandShower*>(GetOwnedCandBase())->fEnergy_wtNC = energy;
00775 break;
00776 case kNC:
00777 dynamic_cast<CandShower*>(GetOwnedCandBase())->fEnergy_NC = energy;
00778 break;
00779 case kEM:
00780 dynamic_cast<CandShower*>(GetOwnedCandBase())->fEnergy_EM = energy;
00781 break;
00782 }
00783 }
00784
00785 Double_t CandShowerHandle::GetEnergy(CandShowerHandle::ShowerType_t showertype) const
00786 {
00787 switch (showertype){
00788 case kWtCC:
00789 return dynamic_cast<const CandShower*>(GetCandBase())->fEnergy_wtCC;
00790 case kCC:
00791 return dynamic_cast<const CandShower*>(GetCandBase())->fEnergy_CC;
00792 case kWtNC:
00793 return dynamic_cast<const CandShower*>(GetCandBase())->fEnergy_wtNC;
00794 case kNC:
00795 return dynamic_cast<const CandShower*>(GetCandBase())->fEnergy_NC;
00796 case kEM:
00797 return dynamic_cast<const CandShower*>(GetCandBase())->fEnergy_EM;
00798 default:
00799 MSG("RecoBase",Msg::kWarning) << " requested shower energy of unknown type " << endl;
00800 return 0;
00801 }
00802 }
00803
00804 void CandShowerHandle::CalibrateEnergy(CandTrackHandle * trk,
00805 AlgConfig & ac){
00806
00807 CandStripHandleItr sItr(GetDaughterIterator());
00808 CandStripHandle * begstrip = sItr();
00809 const VldContext * vld = begstrip->GetVldContext();
00810
00811 Double_t fCCWtLowScale = ac.GetDouble("CCWtLowScale");
00812 Double_t fCCWtLowC1 = ac.GetDouble("CCWtLowC1");
00813 Double_t fCCWtLowC2 = ac.GetDouble("CCWtLowC2");
00814 Double_t fCCWtLowC3 = ac.GetDouble("CCWtLowC3");
00815 Double_t fCCWtLowC4 = ac.GetDouble("CCWtLowC4");
00816 Double_t fCCWtHiC0 = ac.GetDouble("CCWtHiC0");
00817 Double_t fCCWtHiC1 = ac.GetDouble("CCWtHiC1");
00818
00819 Double_t fCCLinLowScale = ac.GetDouble("CCLinLowScale");
00820 Double_t fCCLinLowC1 = ac.GetDouble("CCLinLowC1");
00821 Double_t fCCLinLowC2 = ac.GetDouble("CCLinLowC2");
00822 Double_t fCCLinHiC0 = ac.GetDouble("CCLinHiC0");
00823 Double_t fCCLinHiC1 = ac.GetDouble("CCLinHiC1");
00824
00825 Double_t fNCWtLowScale = ac.GetDouble("NCWtLowScale");
00826 Double_t fNCWtMidScale = ac.GetDouble("NCWtMidScale");
00827 Double_t fNCWtLowC1 = ac.GetDouble("NCWtLowC1");
00828 Double_t fNCWtLowC2 = ac.GetDouble("NCWtLowC2");
00829 Double_t fNCWtLowC3 = ac.GetDouble("NCWtLowC3");
00830 Double_t fNCWtMidC0 = ac.GetDouble("NCWtMidC0");
00831 Double_t fNCWtMidC1 = ac.GetDouble("NCWtMidC1");
00832 Double_t fNCWtMidC2 = ac.GetDouble("NCWtMidC2");
00833 Double_t fNCWtMidC3 = ac.GetDouble("NCWtMidC3");
00834 Double_t fNCWtHiC0 = ac.GetDouble("NCWtHiC0");
00835 Double_t fNCWtHiC1 = ac.GetDouble("NCWtHiC1");
00836
00837 Double_t fNCLinLowScale = ac.GetDouble("NCLinLowScale");
00838 Double_t fNCLinLowC1 = ac.GetDouble("NCLinLowC1");
00839 Double_t fNCLinLowC2 = ac.GetDouble("NCLinLowC2");
00840 Double_t fNCLinHiC0 = ac.GetDouble("NCLinHiC0");
00841 Double_t fNCLinHiC1 = ac.GetDouble("NCLinHiC1");
00842
00843 Double_t fEMLowScale = ac.GetDouble("EMLowScale");
00844 Double_t fEMLowC1 = ac.GetDouble("EMLowC1");
00845 Double_t fEMLowC2 = ac.GetDouble("EMLowC2");
00846 Double_t fEMHiC0 = ac.GetDouble("EMHiC0");
00847 Double_t fEMHiC1 = ac.GetDouble("EMHiC1");
00848
00849 Double_t shw_linmipsum=GetCharge(CalStripType::kMIP);
00850 Double_t shw_wtmipsum=0;
00851 Double_t totshw_wtmipsum=0;
00852 Double_t totshw_linmipsum = GetCharge(CalStripType::kMIP);
00853
00854
00855
00856
00857 Int_t maxpln = 0;
00858 Int_t minpln = 999;
00859 Int_t shared_planes = 0;
00860 Int_t shared_strips = 0;
00861 Int_t nshwstp = 0;
00862 Double_t dedx_1 = 0.;
00863 Double_t dedx_2 = 0.;
00864 Double_t avg_dedx = 0.;
00865 Double_t reco_emu = 0.;
00866 Double_t reco_dircosz = 0.;
00867 Double_t reco_emu_endshw=0.;
00868
00869 if (trk) {
00870 reco_dircosz = fabs(trk->GetDirCosZ());
00871 CandFitTrackHandle* fittrk = dynamic_cast<CandFitTrackHandle*>(trk);
00872 reco_emu = sqrt(trk->GetMomentum()*trk->GetMomentum()+ 0.10566*0.10566);
00873 if(fittrk){
00874 reco_dircosz = fabs(fittrk->GetDirCosZ());
00875 if(fittrk->GetMomentum()>0.) {reco_emu = sqrt(fittrk->GetMomentum()*fittrk->GetMomentum()+ 0.10566*0.10566);}
00876 }
00877
00878 CandStripHandleItr stripItr(GetDaughterIterator());
00879
00880 while (CandStripHandle *strip = dynamic_cast<CandStripHandle*>(stripItr())) {
00881 if (strip) {
00882 nshwstp++;
00883 if((!fittrk && trk->FindDaughter(strip)) || (fittrk && fittrk->FindDaughter(strip))){
00884 shared_strips++;
00885 if(strip->GetPlane()>maxpln) maxpln = strip->GetPlane();
00886 if(strip->GetPlane()<minpln) minpln = strip->GetPlane();
00887 }
00888 }
00889 }
00890 shared_planes = maxpln - minpln + 1;
00891
00892 reco_emu_endshw = reco_emu-shared_planes/(30.*reco_dircosz);
00893
00894 if(fittrk && fittrk->GetPlaneQP(maxpln)!=0.){
00895 Double_t pln_qp = fittrk->GetPlaneQP(maxpln)*(1.013*fabs(fittrk->GetPlaneQP(maxpln)));
00896 reco_emu_endshw = sqrt(1./pln_qp*1./pln_qp + 0.10566*0.10566);
00897 }
00898
00899 if(reco_emu_endshw>reco_emu){reco_emu_endshw = reco_emu-shared_planes/(30.*reco_dircosz);}
00900
00901 dedx_1 = DeDx(reco_emu*1000)/1.985;
00902 if(reco_emu_endshw>0.106){
00903 dedx_2 = DeDx(reco_emu_endshw*1000)/1.985;
00904 avg_dedx = (dedx_1 > dedx_2)? 0.5*(dedx_1+dedx_2):dedx_1;
00905 }
00906 else{avg_dedx = dedx_1;}
00907 shw_linmipsum -= avg_dedx*shared_strips/reco_dircosz;
00908 }
00909 else{
00910 shw_linmipsum=totshw_linmipsum;
00911 }
00912
00913 Double_t CCEnergyLin = (shw_linmipsum<fCCLinLowScale) ? shw_linmipsum*fCCLinLowC1 + shw_linmipsum*shw_linmipsum*fCCLinLowC2: fCCLinHiC0 + shw_linmipsum*fCCLinHiC1;
00914 if(shw_linmipsum<=0) CCEnergyLin=0;
00915
00916 Double_t NCEnergyLin = (totshw_linmipsum<fNCLinLowScale) ? totshw_linmipsum*fNCLinLowC1 + totshw_linmipsum*totshw_linmipsum*fNCLinLowC2: fNCLinHiC0 + totshw_linmipsum*fNCLinHiC1;
00917 if(totshw_linmipsum<=0) NCEnergyLin=0;
00918
00919 Double_t EMEnergy = (totshw_linmipsum<fEMLowScale) ? totshw_linmipsum*fEMLowC1 + totshw_linmipsum*totshw_linmipsum*fEMLowC2: fEMHiC0 + totshw_linmipsum*fEMHiC1;
00920 if(totshw_linmipsum<=0) EMEnergy=0;
00921
00922
00923
00924 Double_t deweightfactorCC = 1.0;
00925 Double_t deweightfactorNC = 1.0;
00926
00927 Double_t fdeweightLowScale = ac.GetDouble("deweightLowScale");
00928 Double_t fdeweightC0 = ac.GetDouble("deweightC0");
00929 Double_t fdeweightC1 = ac.GetDouble("deweightC1");
00930 Double_t fdeweightC2 = ac.GetDouble("deweightC2");
00931 Double_t fdeweightC3 = ac.GetDouble("deweightC3");
00932
00933
00934
00935
00936
00937
00938
00939
00940
00941 double SigHalfPoint = 8.0;
00942 double SigGrad = 0.5;
00943 deweightfactorCC = 0.25 + 0.75/(1. + exp(-(CCEnergyLin-SigHalfPoint)*SigGrad));
00944
00945 if(NCEnergyLin < fdeweightLowScale){
00946 deweightfactorNC = fdeweightC0 +
00947 fdeweightC1 * NCEnergyLin +
00948 fdeweightC2 * NCEnergyLin * NCEnergyLin +
00949 fdeweightC3 * NCEnergyLin * NCEnergyLin * NCEnergyLin;
00950 }
00951
00952
00953 CandStripHandleItr stripItr(GetDaughterIterator());
00954
00955 while (CandStripHandle *strip = dynamic_cast<CandStripHandle*>(stripItr())) {
00956 if (strip) {
00957 totshw_wtmipsum+=pow(GetStripCharge(strip,StripEnd::kWhole),deweightfactorNC);
00958 Double_t trackEloss = 0;
00959
00960 if(trk){
00961 CandFitTrackHandle* fittrk = dynamic_cast<CandFitTrackHandle*>(trk);
00962 if((!fittrk && trk->FindDaughter(strip)) || (fittrk && fittrk->FindDaughter(strip))){
00963 trackEloss=avg_dedx/reco_dircosz;
00964 }
00965 }
00966 if(GetStripCharge(strip,StripEnd::kWhole) - trackEloss > 0){
00967 shw_wtmipsum+=pow(GetStripCharge(strip,StripEnd::kWhole)-trackEloss,deweightfactorCC);
00968 }
00969 }
00970 }
00971
00972 Double_t CCEnergyWt = fCCWtHiC0 + shw_wtmipsum*fCCWtHiC1;
00973 if( shw_wtmipsum<fCCWtLowScale){
00974 CCEnergyWt = shw_wtmipsum*fCCWtLowC1 +
00975 shw_wtmipsum*shw_wtmipsum*fCCWtLowC2 +
00976 shw_wtmipsum*shw_wtmipsum*shw_wtmipsum*fCCWtLowC3 +
00977 shw_wtmipsum*shw_wtmipsum*shw_wtmipsum*shw_wtmipsum*fCCWtLowC4;
00978 }
00979 if(shw_wtmipsum<=0) CCEnergyWt=0;
00980
00981 Double_t NCEnergyWt = fNCWtHiC0 + totshw_wtmipsum*fNCWtHiC1;
00982 if(totshw_wtmipsum<fNCWtLowScale){
00983 NCEnergyWt = totshw_wtmipsum*fNCWtLowC1 +
00984 totshw_wtmipsum*totshw_wtmipsum*fNCWtLowC2 +
00985 totshw_wtmipsum*totshw_wtmipsum*totshw_wtmipsum*fNCWtLowC3;
00986 }
00987
00988 if(totshw_wtmipsum>=fNCWtLowScale && totshw_wtmipsum<fNCWtMidScale){
00989 NCEnergyWt = fNCWtMidC0 + totshw_wtmipsum*fNCWtMidC1 + totshw_wtmipsum*totshw_wtmipsum*fNCWtMidC2 + totshw_wtmipsum*totshw_wtmipsum*totshw_wtmipsum*fNCWtMidC3;
00990 }
00991
00992 if(totshw_wtmipsum<=0) NCEnergyWt=0;
00993
00994
00995
00996
00997
00998
00999
01000 if (vld && vld->GetDetector()==Detector::kNear){
01001 CCEnergyWt *= (.97 + exp(-(CCEnergyWt+11.6)/9.3));
01002 CCEnergyLin *= (.99 + exp(-(CCEnergyLin+28.2)/11.8));
01003 NCEnergyWt *= (1.01 + exp(-(NCEnergyWt+4.33)/5.));
01004 NCEnergyLin *= (1. + exp(-(NCEnergyLin+10.1)/5.));
01005 EMEnergy *= 1.06;
01006 }
01007
01008
01009
01010 if(vld){
01011 float etemplin = CCEnergyLin;
01012 CCEnergyLin = EnergyCorrections::ShowerEnergyConversionDogwood(etemplin,*vld);
01013 etemplin = CCEnergyWt;
01014 CCEnergyWt = EnergyCorrections::WeightedShowerEnergyConversionDogwood(etemplin,*vld);
01015 }
01016
01017
01018 SetEnergy(CCEnergyWt);
01019 SetEnergy(CCEnergyWt,kWtCC);
01020 SetEnergy(CCEnergyLin,kCC);
01021 SetEnergy(NCEnergyWt,kWtNC);
01022 SetEnergy(NCEnergyLin,kNC);
01023 SetEnergy(EMEnergy,kEM);
01024 }
01025
01026
01027
01028 Double_t CandShowerHandle::DeDx(Double_t emu){
01029
01030 Double_t dedx = 0.;
01031 Double_t mm = 105.658389;
01032 Double_t mm_2 = mm*mm;
01033
01034 if(emu*emu-mm_2<0.){return 0.;}
01035
01036 Double_t a_2 = 1./(137.036*137.036);
01037 Double_t pi = 3.141;
01038 Double_t Na = 6.023;
01039 Double_t lamda_2 = 3.8616*3.8616;
01040 Double_t Z_A = 0.5377;
01041 Double_t me = 0.51099906;
01042 Double_t me_2 = me*me;
01043 Double_t beta = sqrt(emu*emu-mm_2)/emu;
01044 Double_t beta_2 = beta*beta;
01045 Double_t gamma = emu/105.658389;
01046 Double_t gamma_2 = gamma*gamma;
01047 Double_t I = 68.7e-6;
01048 Double_t I_2 = I*I;
01049 Double_t p = sqrt(emu*emu-mm_2);
01050 Double_t p_2 = p*p;
01051 Double_t Em = 2 * me * p_2 / ( me_2 + mm_2 + 2*me*emu );
01052 Double_t Em_2= Em*Em;
01053 Double_t emu_2 = emu*emu;
01054 Double_t X0 = 0.165;
01055 Double_t X1 = 2.503;
01056 Double_t X = log10(beta*gamma);
01057 Double_t a = 0.165;
01058 Double_t C = -3.3;
01059 Double_t m = 3.222;
01060 Double_t d = 0;
01061 if(X0 < X && X < X1){d = 4.6052 * X + a * pow(X1-X,m) + C;}
01062 if(X > X1){d = 4.6052 * X + C;}
01063
01064 dedx = a_2 * 2*pi * Na * lamda_2 * Z_A * (me / beta_2) *( log( 2*me*beta_2*gamma_2*Em/I_2 ) - 2*beta_2 + 0.25*(Em_2/emu_2) - d );
01065
01066 return 10*dedx;
01067
01068 }
01069
01070
01071
01072
01073
01074
01075 NavKey CandShowerHandle::KeyFromSlice(const CandShowerHandle *reco)
01076 {
01077 if (reco->GetCandSlice()) {
01078 return static_cast<Int_t>(reco->GetCandSlice()->GetUidInt());
01079 }
01080 return 0;
01081
01082 }
01083
01084
01085
01086
01087
01088 XXXITRIMP(CandShowerHandle)