StRoot  1
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Groups Pages
StEEmcPointFinderIU.cxx
1 
10 #include <TMath.h>
11 
12 #include "StRoot/St_base/StMessMgr.h"
13 #include "StRoot/St_base/Stypes.h"
14 #include "StEEmcUtil/EEmcGeom/EEmcGeomDefs.h"
15 
16 #include "StRoot/StEEmcPool/./EEmcTreeContainers/EEmcEnergy.h"
17 #include "StRoot/StEEmcPool/StEEmcGeoId/StEEmcGeoId.h"
18 
19 #include "StEEmcPointFinderIU.h"
20 #include "StFinderAlg.h"
21 #include "StSimpleCluster.h"
22 #include "StEEmcHit.h"
23 #include "StEEmcStripClusterFinder.h"
24 #include "StESMDClustersPerSector.h"
25 
26 StEEmcPointFinderIU_t::StEEmcPointFinderIU_t() : StEEmcPointFinder_t(),
27  mEEmcSmdGeom( 0 ),
28  mEEmcSmdMap( 0 ),
29  mMinUVratio( 0 ),
30  mZratioThres( 0.2 ),
31  mTtestThres( 9.e9 ),
32  mUseBugFixes( 1 ),
33  mTowerThreshold( 0.0 )
34 {
35  mEEmcSmdGeom = EEmcSmdGeom::instance();
36  mEEmcSmdMap = EEmcSmdMap::instance();
37 
38  if( !mEEmcSmdGeom ){
39  LOG_FATAL << "StEEmcPointFinderIU_t(...) CANNOT GET POINTER TO EEmcSmdGeom" << endm;
40  return;
41  };
42 
43  if( !mEEmcSmdMap ){
44  LOG_FATAL << "StEEmcPointFinderIU_t(...) CANNOT GET POINTER TO EEmcSmdMap" << endm;
45  return;
46  };
47 
48  mIsReady = 1;
49 };
50 
56 Int_t StEEmcPointFinderIU_t::find( const EEmcEnergy_t& eemcEnergy,
57  const StSimpleClusterVec_t &towerClusterVec,
58  const StESMDClustersVec_t &smdClusterVec,
59  const Double_t* smdEuEvRatio, // not used
60  StEEmcHitVec_t& hitVec ){
61 
62  //LOG_INFO << "********** StEEmcPointFinderIU_t::find(...) **********" << endm;
63 
64  Int_t ierr = kStOK;
65 
66  // Want to make a pool of cluster pointers. The pool needs to
67  // be a linked list, so that clusters can be efficiently
68  // removed.
69  StClusterPool_t uClusterPool, vClusterPool;
70 
71  // define some iterators
72  StESMDClustersVec_t::const_iterator smdClusterVecIter;
73  StSimpleClusterVec_t::const_iterator clusterIter;
74 
75  // last hit ID
76  mLastSMDhitID = -1;
77 
78  // iterate over sectors with at least one cluster
79  for( smdClusterVecIter = smdClusterVec.begin(); smdClusterVecIter != smdClusterVec.end(); ++smdClusterVecIter ){
80  mSector = smdClusterVecIter->getSector();
81 
82  //LOG_INFO << "mSector = " << mSector << " (" << (Int_t)(smdClusterVecIter-smdClusterVec.begin()) << " of " << smdClusterVec.size() << ")" << endm;
83 
84  // clear the pools
85  uClusterPool.clear();
86  vClusterPool.clear();
87 
88  // some references to make code cleaner
89  const StSimpleClusterVec_t &uClusVec = smdClusterVecIter->getClusterVecU();
90  const StSimpleClusterVec_t &vClusVec = smdClusterVecIter->getClusterVecV();
91 
92  //LOG_INFO << "--> Num clusters = " << uClusVec.size() << ' ' << vClusVec.size() << endm;
93 
94  // u layer
95  for( clusterIter = uClusVec.begin(); clusterIter != uClusVec.end(); ++clusterIter )
96  uClusterPool.insert( &(*clusterIter) );
97 
98  // v layer
99  for( clusterIter = vClusVec.begin(); clusterIter != vClusVec.end(); ++clusterIter )
100  vClusterPool.insert( &(*clusterIter) );
101 
102  // No need to sort, since the StClusterPool_t is a set (automatically ordered)
103  //std::sort( uClusterPool.begin(), uClusterPool.end(), &StEEmcPointFinderIU_t::clusterLessThan );
104  //std::sort( vClusterPool.begin(), vClusterPool.end(), &StEEmcPointFinderIU_t::clusterLessThan );
105 
106  // find the points, i.e. hits (a recursive algorithm)
107  ierr = findPoints( eemcEnergy, uClusterPool, vClusterPool, hitVec );
108 
109  //LOG_INFO << "--> Number of hits " << hitVec.size() << endm;
110  };
111 
112 
113  // return the error code
114  return ierr;
115 };
116 
117 // need to make u and v cluster vectors are not constant?
119  StClusterPool_t &uClusterPool,
120  StClusterPool_t &vClusterPool,
121  StEEmcHitVec_t& hitVec ) {
122 
123  Int_t ierr = kStOK;
124 
125  // --------------- build SMD points ---------------
126 
127  // First try finding all candidate hits. Any pair of u & v
128  // clusters under an "active" tower are considered candidates, with
129  // "active" being defined below
130 
131  // containter for all possible hits to consider
132  // Call these the stage 0 hits
133  StEEmcHitVec_t hitsSMDstage0;
134 
135  // Container for hits still available after stage 1 Note: can store
136  // the index value. Since stage 0 is sorted by ttest^2, sorting by
137  // index value will also sort by ttest^2.
138  std::vector< Int_t > hitIdxStage1;
139 
140  // container for hits still available after stage 2
141  std::vector< Int_t > hitIdxStage2;
142 
143  //LOG_INFO << "Building candidate points" << endm;
144 
145  // iterators
146  StClusterPool_t::const_iterator uClusIter;
147  StClusterPool_t::const_iterator vClusIter;
148 
149 
150  //LOG_INFO << "U Pool " << endm;
151 // for( uClusIter = uClusterPool.begin(); uClusIter != uClusterPool.end(); ++uClusIter ){
152 // //LOG_INFO << *uClusIter << endm;
153 // };
154 // //LOG_INFO << "V Pool " << endm;
155 // for( vClusIter = vClusterPool.begin(); vClusIter != vClusterPool.end(); ++vClusIter ){
156 // //LOG_INFO << *vClusIter << endm;
157 // };
158 
159  //LOG_INFO << " iii " << mSector << ": pool sizes " << uClusterPool.size() << ' ' << vClusterPool.size() << endm;
160 
161  // iterate over u and v clusters to make pairs
162  for( uClusIter = uClusterPool.begin(); uClusIter != uClusterPool.end() && !ierr; ++uClusIter ){
163  for( vClusIter = vClusterPool.begin(); vClusIter != vClusterPool.end() && !ierr; ++vClusIter ){
164 
165  // get the index of the seed strips of the clusters. index
166  // is with reference to the indexing of the strips in the
167  // sector, not the strips within the cluster.
168  //Int_t uSeedIdx = (*uClusIter)->getSeedMember();
169  //Int_t vSeedIdx = (*vClusIter)->getSeedMember();
170  Float_t uSeedMean = (*uClusIter)->getMeanX();
171  Float_t vSeedMean = (*vClusIter)->getMeanX();
172 
173  assert( uSeedMean >= 0 && vSeedMean >= 0 && uSeedMean < kEEmcNumStrips && vSeedMean < kEEmcNumStrips ); // fix the clustering code
174  //LOG_INFO << "seed indices " << uSeedMean << ' ' << vSeedMean << ", sector is " << mSector << endm;
175 
176  // determine which tower this SMD point/hit is under
177  Bool_t isValid = 0;
178 
179  TVector3 direct = mEEmcSmdGeom->getIntersection( mSector, uSeedMean, vSeedMean );
180  Int_t sec,sub,eta;
181  if( mEEmcGeomSimple.getTower(direct,sec,sub,eta) ){
182  // is valid tower, check sectors agree
183  isValid = ( sec == mSector );
184  };
185 
186  //LOG_INFO << " rrr " << getEventNum() << ' ' << mSector << ' ' << uSeedIdx << ' ' << vSeedIdx << ' ' << uSeedMean << ' ' << vSeedMean << ' '
187  // << direct.X() << ' ' << direct.Y() << ' ' << direct.Z() << endm;
188 
189 
190  //LOG_INFO << "zzz " << sec << ' ' << mSector << endm;
191 
192  Int_t hitTowerIdx = StEEmcGeoId_t::encodeTow( sec, sub, eta );
193  const EEmcElement_t& tower = eemcEnergy.eTow.getByIdx( hitTowerIdx );
194 
195  Float_t uE = 0;
196  Float_t vE = 0;
197 
198  isValid = 0;
199 
200  // the following is what is meant by "active":
204  if ( tower.energy > mTowerThreshold ) {
205  isValid = 1;
206  } else if ( tower.fail ) {
207  isValid = ( eemcEnergy.ePre1.getByIdx( hitTowerIdx ).energy > 0 ||
208  eemcEnergy.ePre2.getByIdx( hitTowerIdx ).energy > 0 ||
209  eemcEnergy.ePost.getByIdx( hitTowerIdx ).energy > 0 );
210  };
211  //LOG_INFO << "Active OK? " << isValid << endm;
212 
213  if( isValid ){
214  // compute the energy of the two clusters
215  uE = (*uClusIter)->getEnergy();
216  vE = (*vClusIter)->getEnergy();
217 
220  isValid &= uE > mMinUVratio*vE;
221  isValid &= vE > mMinUVratio*uE;
222  };
223 
224  //LOG_INFO << "E matching OK? " << isValid << ' ' << mMinUVratio << ' ' << uE << ' ' << vE << endm;
225 
226  if( isValid ) {
227  //LOG_INFO << "Valid point with seeds " << (*uClusIter)->getID() << ' ' << (*vClusIter)->getID() << endm;
228 
229  // push back a potential hit
230  hitsSMDstage0.push_back( StEEmcHit_t(++mLastSMDhitID) );
231 
232  // get reference
233  StEEmcHit_t &hit = hitsSMDstage0.back();
234 
235  // set UV info
236  hit.setEnergyU( uE );
237  hit.setEnergyV( vE );
238  hit.setClusIDu( (*uClusIter)->getID() );
239  hit.setClusIDv( (*vClusIter)->getID() );
240  hit.setTowerIdx( hitTowerIdx );
241  hit.setSector( mSector );
242 
243  // pre-compute ttest value
244  hit.computeTtest2();
245 
246  // determine position (actually already did earlier, and
247  // called it direct)
248  //TVector3 position = mEEmcSmdGeom->getIntersection( mSector, uSeedMean, vSeedMean );
249  hit.setX( direct.X() );
250  hit.setY( direct.Y() );
251  hit.setZ( direct.Z() );
252 
253  //LOG_INFO << "position = " << direct.X() << ' ' << direct.Y() << ' ' << direct.Z() << endm;
254 
255  //LOG_INFO << "Potential hit: " << hit << endm;
256  //LOG_INFO << *(*uClusIter) << endm;
257  //LOG_INFO << *(*vClusIter) << endm;
258 
259  //LOG_INFO << ", clus IDs " << hit.getClusIDu() << ' ' << hit.getClusIDv() << ", tow " << hit.getTowerIdx() << endm;
260 
261  if( direct.Z() < -998 ){
262  // bad pairing, remove the candidate hit
263  hitsSMDstage0.pop_back();
264  };
265 
266  //LOG_INFO << "stage 0 candidate: " << mLastSMDhitID << ' ' << (*uClusIter)->getSeedMember() << ' ' << (*vClusIter)->getSeedMember() << endm;
267 
268  }; // end if( isValid )
269  };
270  // end loop over v clusters
271  };
272  // end loop over u v clusters
273 
274  //LOG_INFO << "\tstage 0 candidates " << hitsSMDstage0.size() << endm;
275 
276 
277  //LOG_INFO << "At stage 0, exists " << hitsSMDstage0.size() << " candidates" << endm;
278 
279  // ---------------- prepare for stage 1 and 2 ---------------
280 
281  // if not enough candidate hits, then give up trying (or if there was an error)
282  // Note: this is not an error, but a stopping criteria
283  if( hitsSMDstage0.size() < 1 || ierr )
284  return ierr;
285 
286  // sort SMD candidate hits according to ttest, which is currently
287  // stored in the energy field of the hit
288  std::sort( hitsSMDstage0.begin(), hitsSMDstage0.end(), hitTtest2LessThan );
289 
293  std::map< Int_t, std::vector<Int_t> > uClusID2hitIdx, vClusID2hitIdx;
294 
295  // also create associative array between cluster indices and pointers to the clusters
296  std::map< Int_t, const StSimpleCluster_t* > uClusID2ptr, vClusID2ptr;
297  for( uClusIter = uClusterPool.begin(); uClusIter != uClusterPool.end(); ++uClusIter )
298  uClusID2ptr[ (*uClusIter)->getID() ] = (*uClusIter);
299 
300  for( vClusIter = vClusterPool.begin(); vClusIter != vClusterPool.end(); ++vClusIter )
301  vClusID2ptr[ (*vClusIter)->getID() ] = (*vClusIter);
302 
303 
304  for( UInt_t i=0; i < hitsSMDstage0.size(); i++ ) {
305 // {
306 // //LOG_INFO << "Stage0 hit " << i << ' ' << hitsSMDstage0[i].getID() << ", ttest " << hitsSMDstage0[i].getTtest2() << ", clus seeds ";
307 // //LOG_INFO << uClusID2ptr[ hitsSMDstage0[i].getClusIDu() ]->getSeedMember() << ", ";
308 // //LOG_INFO << vClusID2ptr[ hitsSMDstage0[i].getClusIDv() ]->getSeedMember() << endm;
309 // const StSimpleCluster_t &uClus = *uClusID2ptr[ hitsSMDstage0[i].getClusIDu() ];
310 // const StSimpleCluster_t &vClus = *vClusID2ptr[ hitsSMDstage0[i].getClusIDv() ];
311 // //LOG_INFO << "-----> layer U, SMD cluster: " << uClus << endm;
312 // //LOG_INFO << "-----> layer V, SMD cluster: " << vClus << endm;
313 // Float_t ttest = (uClus.getEnergy()-vClus.getEnergy())/(uClus.getEnergy()+vClus.getEnergy());
314 // //LOG_INFO << "----------> T-test = " << ttest << ", T-test^2 = " << ttest*ttest << endm;
315 // };
316  // renumber hits, just to make sure ordering is consistant
317 
318  //LOG_INFO << "Hit ID " << hitsSMDstage0[i].getID() << " -> " << i << endm;
319 
320  //hitsSMDstage0[i].setID( i );
321 
322  //LOG_INFO << "Adding hit " << i << ", " << hitsSMDstage0[i].getID() << " with u, v clus idx " << hitsSMDstage0[i].getClusIDu() << ", " << hitsSMDstage0[i].getClusIDv() << endm;
323 
324  // note: hit index is the index in the hitsSMDstage0 array
325  uClusID2hitIdx[ hitsSMDstage0[i].getClusIDu() ].push_back( i );
326  vClusID2hitIdx[ hitsSMDstage0[i].getClusIDv() ].push_back( i );
327 
328  //uClusID2hitIdx[ hitsSMDstage0[i].getClusIDu() ].push_back( hitsSMDstage0[i].getID() );
329  //vClusID2hitIdx[ hitsSMDstage0[i].getClusIDv() ].push_back( hitsSMDstage0[i].getID() );
330  };
331 
332 
333 
334  // not in original IU code: remove clusters from the pool that have no stage 0 points
335  for( uClusIter = uClusterPool.begin(); uClusIter != uClusterPool.end(); ){
336  const StSimpleCluster_t* clusPtr = (*uClusIter);
337 
338  if( uClusID2hitIdx[ clusPtr->getID() ].empty() ){
339  // move the iterator first
340  ++uClusIter;
341 
342  // now delete from the set
343  uClusterPool.erase( clusPtr );
344  } else {
345  ++uClusIter;
346  };
347  };
348 
349  for( vClusIter = vClusterPool.begin(); vClusIter != vClusterPool.end(); ){
350  const StSimpleCluster_t* clusPtr = (*vClusIter);
351 
352  if( vClusID2hitIdx[ clusPtr->getID() ].empty() ){
353  // move the iterator first
354  ++vClusIter;
355 
356  // now delete from the set
357  vClusterPool.erase( clusPtr );
358  } else {
359  ++vClusIter;
360  };
361  };
362 
363 
364 
365  //LOG_INFO << "stage 1: stage0 candiates = " << hitsSMDstage0.size() << endm;
366 
367 
368  // ---------------- STAGE 1 ---------------
369 
370  // iterate over clusters, saving those clusters which only appear in a single hit
371  // about line 330 of StEEmcIUPointMaker.cxx
372 
373  //LOG_INFO << "looping over " << uClusterPool.size() << " u clusters" << endm;
374 
375  for( uClusIter = uClusterPool.begin(); uClusIter != uClusterPool.end(); ++uClusIter ){
376  // get reference to array of associated hit indices
377 
378  //LOG_INFO << "U cluster ID = " << (*uClusIter)->getID() << endm;
379 
380  std::vector<Int_t>& hitIdxVec = uClusID2hitIdx[ (*uClusIter)->getID() ];
381 
382  //LOG_INFO << "Number of hits associated with this cluster " << hitIdxVec.size() << endm;
383 
384  // check how many possible hits are associated with the given
385  // U cluster
386  if( !hitIdxVec.empty() ){
387  if( hitIdxVec.size() == 1 ){
388  // only one, so add it to the stage 1 list of possible hits/points
389  hitIdxStage1.push_back( hitIdxVec.front() );
390  //LOG_INFO << "Pushing back stage 1: " << hitIdxVec.front() << endm;
391  };
392 
393  //LOG_INFO << "Deciding whether to push back into stage 2: " << hitIdxVec.front() << " or " << hitIdxVec.back() << endm;
394 
395  // state two includes the best of the options (the one in front)
396  hitIdxStage2.push_back( hitIdxVec.front() );
397  };
398  };
399 
400  //LOG_INFO << "looping over " << vClusterPool.size() << " v clusters" << endm;
401 
402  for( vClusIter = vClusterPool.begin(); vClusIter != vClusterPool.end(); ++vClusIter ){
403  // get reference to array of associated hit indices
404 
405  //LOG_INFO << "V cluster ID = " << (*vClusIter)->getID() << endm;
406 
407  std::vector<Int_t>& hitIdxVec = vClusID2hitIdx[ (*vClusIter)->getID() ];
408 
409  //LOG_INFO << "Number of hits associated with this cluster " << hitIdxVec.size() << endm;
410 
411  // check how many possible hits are associated with the given
412  // V cluster
413  if( !hitIdxVec.empty() ){
414  if( hitIdxVec.size() == 1 ){
415  // only one, so add it to the stage 1 list of possible hits/points
416  hitIdxStage1.push_back( hitIdxVec.front() );
417 
418  //LOG_INFO << "Pushing back stage 1: " << hitIdxVec.front() << endm;
419  };
420 
421  //LOG_INFO << "Deciding whether to push back into stage 2: " << hitIdxVec.front() << " or " << hitIdxVec.back() << endm;
422 
423  // state two includes the best of the options (the one in front)
424  hitIdxStage2.push_back( hitIdxVec.front() );
425  };
426  };
427 
428  // Note: in the case of only one u and only one v cluster, the
429  // cluster will appear twice in the hitIdxStage1 vector. Bug fixes
430  // can be turned on or off with the mUseBugFixes variable.
431 
432  // since stage 0 is sorted, is sufficient to sort the indices in the stage1 vectors
433  std::sort( hitIdxStage1.begin(), hitIdxStage1.end() );
434 
435  //LOG_INFO << "Number of stage 1 = " << hitIdxStage1.size() << ", stage 2 = " << hitIdxStage2.size() << endm;
436 
437 // //LOG_INFO << "STAGE 1" << endm;
438 // for( UInt_t i=0; i<hitIdxStage1.size(); ++i ){
439 // StEEmcHit_t &hit = hitsSMDstage0[ hitIdxStage1[i] ];
440 // //LOG_INFO << "Stage1[" << i << "] = " << hit.getTtest2() << endm;
441 // //LOG_INFO << "\t" << *uClusID2ptr[ hit.getClusIDu() ] << endm;
442 // //LOG_INFO << "\t" << *vClusID2ptr[ hit.getClusIDv() ] << endm;
443 // };
444 
445 // //LOG_INFO << "STAGE 2" << endm;
446 // for( UInt_t i=0; i<hitIdxStage2.size(); ++i ){
447 // StEEmcHit_t &hit = hitsSMDstage0[ hitIdxStage2[i] ];
448 // //LOG_INFO << "Stage2[" << i << "] = " << hit.getTtest2() << endm;
449 // //LOG_INFO << "\t" << *uClusID2ptr[ hit.getClusIDu() ] << endm;
450 // //LOG_INFO << "\t" << *vClusID2ptr[ hit.getClusIDv() ] << endm;
451 // };
452 
453  //LOG_INFO << "checking if splitting needed" << endm;
454 
455  // check if splitting needed
456  if( hitIdxStage1.size() > 1 ){
457  std::vector< Int_t >::iterator hitIter_1, hitIter_2;
458 
459  for( hitIter_1 = hitIdxStage1.begin(); hitIter_1 != hitIdxStage1.end(); ++hitIter_1 ){
460  StEEmcHit_t &hit1 = hitsSMDstage0[ *hitIter_1 ];
461  const StSimpleCluster_t *Uclus1 = uClusID2ptr[ hit1.getClusIDu() ];
462  const StSimpleCluster_t *Vclus1 = vClusID2ptr[ hit1.getClusIDv() ];
463 
464  hitIter_2 = hitIter_1;
465 
466  ++hitIter_2;
467  if( mUseBugFixes ){
468  // move the second iter until it no longer points to the same hit
469  while( (*hitIter_2) == (*hitIter_1) && hitIter_2 != hitIdxStage1.end())
470  ++hitIter_2;
471  };
472 
473  for( ; hitIter_2 != hitIdxStage1.end(); ++hitIter_2 ){
474  //LOG_INFO << "hitIters point at " << *hitIter_1 << ' ' << *hitIter_2 << endm;
475  //LOG_INFO << "stage 0 hits of size " << hitsSMDstage0.size() << endm;
476 
477  StEEmcHit_t &hit2 = hitsSMDstage0[ *hitIter_2 ];
478  const StSimpleCluster_t *Uclus2 = uClusID2ptr[ hit2.getClusIDu() ];
479  const StSimpleCluster_t *Vclus2 = vClusID2ptr[ hit2.getClusIDv() ];
480 
481  // now just work with Uclus1, Uclus2, Vclus1, Vclus2
482 
483  // Note: it is unclear why there are 'aa' and 'bb'
484  // variables used in the older implementation, as they are
485  // only incremented after the return statements, and thus
486  // are always zero.
487 
488  Bool_t oneU = ( Uclus1 == Uclus2 );
489  Bool_t oneV = ( Vclus1 == Vclus2 );
490 
491  if( oneU ^ oneV ){
492  // either 2x1 or 1x2
493 
494  Bool_t isBelowThres = 0;
495  Float_t uZratio, vZratio, uWeight1, uWeight2, vWeight1, vWeight2;
496 
497  //LOG_INFO << "a2a2a2 E = "
498  // << Uclus1->getEnergy()*hit1.getWeightU() << ' ' << Vclus1->getEnergy()*hit1.getWeightV() << ' '
499  // << Uclus2->getEnergy()*hit2.getWeightU() << ' ' << Vclus2->getEnergy()*hit2.getWeightV() << ' '
500  // << endm;
501 
502  if( oneU ){
503  // Weihong calls this uzr, presumably for the u Z-ratio
504  uZratio = TMath::Abs(
505  ( Uclus1->getEnergy() - Vclus1->getEnergy() - Vclus2->getEnergy() )/
506  ( Uclus1->getEnergy() + Vclus1->getEnergy() + Vclus2->getEnergy() ) );
507  vZratio = 1;
508 
509  // Weihong hard codes mZratioThres = 0.2
510  isBelowThres = ( uZratio < mZratioThres );
511 
512  uWeight1 = Vclus1->getEnergy()/(Vclus1->getEnergy()+Vclus2->getEnergy());
513  uWeight2 = 1 - uWeight1; // == Vclus2->getEnergy()/(Vclus1->getEnergy()+Vclus2->getEnergy());
514  vWeight1 = 1;
515  vWeight2 = 1;
516 
517  //LOG_INFO << "a2a2a2a " << uZratio << " vs " << mZratioThres << "\t" << uWeight1 << ' ' << uWeight2 << endm;
518  } else {
519  uZratio = 1;
520  vZratio = TMath::Abs(
521  ( Vclus1->getEnergy() - Uclus1->getEnergy() - Uclus2->getEnergy() )/
522  ( Vclus1->getEnergy() + Uclus1->getEnergy() + Uclus2->getEnergy() ) );
523 
524  // Weihong hard codes mZratioThres = 0.2
525  isBelowThres = ( vZratio < mZratioThres );
526  //LOG_INFO << "b) " << vZratio << " vs " << mZratioThres << endm;
527 
528  uWeight1 = 1;
529  uWeight2 = 1;
530  vWeight1 = Uclus1->getEnergy()/(Uclus1->getEnergy()+Uclus2->getEnergy());
531  vWeight2 = 1 - vWeight1; // == Uclus2->getEnergy()/(Uclus1->getEnergy()+Uclus2->getEnergy());
532 
533  //LOG_INFO << "a2a2a2b " << vZratio << " vs " << mZratioThres << "\t" << vWeight1 << ' ' << vWeight2 << endm;
534  };
535 
536  //LOG_INFO << "checking if is below threshold" << endm;
537 
538  if( isBelowThres ){
539  //LOG_INFO << "it is" << endm;
540 
541  // make two new hits by copying the current two hits
542  hitVec.push_back( hit1 );
543  StEEmcHit_t &saved_hit1 = hitVec.back();
544 
545  hitVec.push_back( hit2 );
546  StEEmcHit_t &saved_hit2 = hitVec.back();
547 
548  // need to set new weights
549  saved_hit1.setWeightU( uWeight1 );
550  saved_hit1.setWeightV( vWeight1 );
551  saved_hit2.setWeightU( uWeight2 );
552  saved_hit2.setWeightV( vWeight2 );
553 
554  // Note: not adjusting keys as done in Weihong's code
555 
556  // remove clusters
557  uClusterPool.erase( Uclus1 );
558  vClusterPool.erase( Vclus1 );
559  if( !oneU )
560  uClusterPool.erase( Uclus2 );
561  if( !oneV )
562  vClusterPool.erase( Vclus2 );
563 
564  //LOG_INFO << "aaa " << getEventNum() << ' ' << mSector << " 2x1 " <<
565  // Uclus1->getSeedMember() << ' ' << Vclus1->getSeedMember() << ' ' <<
566  // Uclus2->getSeedMember() << ' ' << Vclus2->getSeedMember() << ' ' <<
567  // Uclus1->getEnergy() << ' ' << Vclus1->getEnergy() << ' ' <<
568  // Uclus2->getEnergy() << ' ' << Vclus2->getEnergy() << ' ' <<
569  // " | " << saved_hit1.getID() << ' ' << saved_hit2.getID() << endm;
570  //LOG_INFO << "aaa, Sector " << mSector << "\t";
571  //LOG_INFO << "2x1 found with seed indices " << Uclus1->getSeedMember() << ' ' << Vclus1->getSeedMember() << ' ' << Uclus2->getSeedMember() << ' ' << Vclus2->getSeedMember() << endm;
572 
573  // recursive algo (high memory cost!!!)
574  return findPoints( eemcEnergy, uClusterPool, vClusterPool, hitVec );
575  };
576  };
577 
578  //if( oneU && oneV ){
579  // Weihong's code calls this case 3
580 
581  // Note: in this case (and in several other places)
582  // Weihong's code copies all hits to a new container.
583  // This is not really needed.
584  //};
585 
586  // Note: Weihong's code does no do anything yet for cases
587  // except except 2x1 and 1x2. This is enforced
588  // earlier also, since only hits which had at least a
589  // unique u or v is considered in stage one.
590  };
591  };
592  };
593 
594  // Haven't found a good pair yet, but have only tried 2x1 and 1x2
595  // configurations. Now look for a good "1x1" configuration, or
596  // actually best of that which is left, as Weihong coded it.
597 
598  // no need to iterate to find "the best", it is the last one in the list,
599  // as the list is sorted.
600 
601  //LOG_INFO << "checking for 1x1 config" << endm;
602 
603  // check if there even is a 1x1 option
604  if( !hitIdxStage1.empty() ){
605  //LOG_INFO << "Yep!" << endm;
606 
607 // for( UInt_t i=0; i<hitIdxStage1.size(); ++i ){
608 // StEEmcHit_t &hit = hitsSMDstage0[ hitIdxStage1[i] ];
609 // //LOG_INFO << "Stage1[" << i << "] = " << hit.getTtest2() << endm;
610 // //LOG_INFO << "\t" << *uClusID2ptr[ hit.getClusIDu() ] << endm;
611 // //LOG_INFO << "\t" << *vClusID2ptr[ hit.getClusIDv() ] << endm;
612 // };
613 
614  StEEmcHit_t &hit = hitsSMDstage0[ hitIdxStage1.front() ];
615 
616  //LOG_INFO << "Got stage0[" << hitIdxStage1.front() << "] of " << hitsSMDstage0.size() << ", hit: " << hit << endm;
617 
618  const StSimpleCluster_t *uClus = uClusID2ptr[ hit.getClusIDu() ];
619  const StSimpleCluster_t *vClus = vClusID2ptr[ hit.getClusIDv() ];
620 
621  //LOG_INFO << "Checking ttest^2: " << hit.getTtest2() << " <? " << mTtestThres << endm;
622 
623  // Wiehong hardcodes mTtestThres to be 9.0e9
624  if( hit.getTtest2() < mTtestThres ){
625  // save a copy of this hit
626  hitVec.push_back( hit );
627 
628  // remove the clusters
629  uClusterPool.erase( uClus );
630  vClusterPool.erase( vClus );
631 
632  //LOG_INFO << "erased " << uClus << ' ' << vClus << endm;
633 
634  //LOG_INFO << "__--> 1x1 found, recursing, but now pools of size " << uClusterPool.size() << ' ' << vClusterPool.size() << endm;
635 
636  //LOG_INFO << "aaa, Sector " << mSector << "\t";
637  //LOG_INFO << "1x1 found with seed indices " << uClus->getSeedMember() << ' ' << vClus->getSeedMember() << endm;
638  //LOG_INFO << "aaa " << getEventNum() << ' ' << mSector << " 1x1 " <<
639  // uClus->getSeedMember() << ' ' << vClus->getSeedMember() << ' ' <<
640  // uClus->getEnergy() << ' ' << vClus->getEnergy() <<
641  // " | " << hit.getID() << endm;
642 
643  // recurse
644  return findPoints( eemcEnergy, uClusterPool, vClusterPool, hitVec );
645  };
646  };
647 
648  //LOG_INFO << "stage 2" << endm;
649 
650  // ---------------- STAGE 2 ---------------
651 
652  // no luck finding matches yet.
653 
654  // Weihong does a fair amount of work to determine what the hit
655  // with the best t-test is. It seems this is due misperceptions
656  // regarding scoping and recursion. It seems the code of Weihong
657  // tries to find the point with the smallest asymmetry in the
658  // cluster energies (what he calls chi^2), but only search amoung
659  // points where either the u or v cluster belongs to only one
660  // candidate hit. The largest element of the hitIdxState2 array is
661  // already the element that Weihong seems to be after.
662 
663  // make sure there is at least one option
664  if( !hitIdxStage2.empty() ){
665  // find the largest element
666  // since put u and v in seperately, stage2 is not sorted.
667  Int_t idx = *(std::min_element( hitIdxStage2.begin(), hitIdxStage2.end() ));
668 
669 // //LOG_INFO << "Stage 2:" << endm;
670 // for( UInt_t i = 0; i<hitIdxStage2.size(); ++i ){
671 // StEEmcHit_t &hit = hitsSMDstage0[ hitIdxStage2[i] ];
672 // const StSimpleCluster_t *uClus = uClusID2ptr[ hit.getClusIDu() ];
673 // const StSimpleCluster_t *vClus = vClusID2ptr[ hit.getClusIDv() ];
674 
675 // //LOG_INFO << i << ' ' << hit.getID() << ", ttest " << hit.getTtest2() << ", seed indices " << uClus->getSeedMember() << ' ' << vClus->getSeedMember();
676 // //LOG_INFO << ' ' << uClus->getEnergy() << ' ' << vClus->getEnergy() << endm;
677 // };
678 
679  StEEmcHit_t &hit = hitsSMDstage0[ idx ];
680  const StSimpleCluster_t *uClus = uClusID2ptr[ hit.getClusIDu() ];
681  const StSimpleCluster_t *vClus = vClusID2ptr[ hit.getClusIDv() ];
682 
683  // Wiehong hardcodes mTtestThres to be 9.0e9
684  if( hit.getTtest2() < mTtestThres ){
685  // save a copy of this hit
686  hitVec.push_back( hit );
687 
688  // remove the clusters
689  uClusterPool.erase( uClus );
690  vClusterPool.erase( vClus );
691 
692  //LOG_INFO << "aaa " << getEventNum() << ' ' << mSector << " last " <<
693  // uClus->getSeedMember() << ' ' << vClus->getSeedMember() << ' ' <<
694  // uClus->getEnergy() << ' ' << vClus->getEnergy() <<
695  // " | " << hit.getID() << endm;
696 
697  //LOG_INFO << "aaa, Sector " << mSector << "\t";
698  //LOG_INFO << "last case " << idx << ' ' << hit.getID() << " with seed indices " << uClus->getSeedMember() << ' ' << vClus->getSeedMember() << endm;
699 
700  // recurse
701  return findPoints( eemcEnergy, uClusterPool, vClusterPool, hitVec );
702  };
703  };
704 
705  // will probably never get here
706  return kStOk;
707 };
708 
709 ClassImp( StEEmcPointFinderIU_t );
710 
711 /*
712  * $Id: StEEmcPointFinderIU.cxx,v 1.2 2013/02/21 22:00:44 sgliske Exp $
713  * $Log: StEEmcPointFinderIU.cxx,v $
714  * Revision 1.2 2013/02/21 22:00:44 sgliske
715  * general update
716  *
717  * Revision 1.1 2012/11/26 19:05:55 sgliske
718  * moved from offline/users/sgliske/StRoot/StEEmcPool/StEEmcHitMaker to StRoot/StEEmcPool/StEEmcHitMaker
719  *
720  *
721  */
Int_t findPoints(const EEmcEnergy_t &eemcEnergy, StClusterPool_t &uClusterVec, StClusterPool_t &vClusterVec, StEEmcHitVec_t &hitVec)
virtual Int_t find(const EEmcEnergy_t &eemcEnergy, const StSimpleClusterVec_t &towerClusterVec, const StESMDClustersVec_t &smdClusterVec, const Double_t *smdEuEvRatio, StEEmcHitVec_t &hitVec)
find some some points
The class.
Definition: StEEmcHit.h:37
Definition: Stypes.h:40
TVector3 getIntersection(Int_t iSec, Int_t iUStrip, Int_t iVStrip, const TVector3 &vertex) const
bool getTower(const TVector3 &r, int &sec, int &sub, int &etabin, Float_t &dphi, Float_t &deta) const
Definition: Stypes.h:41