StRoot  1
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Groups Pages
StSstClusterList.cc
1 //$Id: StSstClusterList.cc,v 1.4 2021/05/12 00:06:10 perev Exp $
2 //
3 //$Log: StSstClusterList.cc,v $
4 //Revision 1.4 2021/05/12 00:06:10 perev
5 //Add std::
6 //
7 //Revision 1.3 2016/05/26 14:10:34 bouchet
8 //cpp-check for leak in splitCluster()
9 //
10 //Revision 1.2 2015/06/24 17:37:21 smirnovd
11 //StSstUtil: Prepend included headers with path to submodule
12 //
13 //Revision 1.1 2015/06/23 16:26:20 jeromel
14 //First version created from the SSD code and reshaped
15 //
16 //Revision 1.1 2015/04/19 17:30:31 bouchet
17 //initial commit ; SST codes
18 //
19 
20 //fork from the SSD code, move along - see history therein
21 
22 #include <vector>
23 #include "StSstUtil/StSstClusterList.hh"
24 #include "StSstUtil/StSstClusterControl.h"
25 #include "StSstUtil/StSstCluster.hh"
26 #include "StSstStripList.hh"
27 #include "St_base/Stiostream.h"
28 #include <math.h>
29 
30 StSstClusterList::StSstClusterList()
31 {
32  mListLength = 0;
33  mFirstCluster = 0;
34  mLastCluster = 0;
35 }
36 
37 StSstClusterList::~StSstClusterList()
38 {
39  if (mListLength)
40  {
41  StSstCluster *ptr = mLastCluster;
42  StSstCluster *toDele;
43  while (mListLength)
44  {
45  toDele = ptr;
46  ptr = prev(ptr);
47  delete toDele;
48  mListLength--;
49  }
50  }
51 }
52 
53 StSstCluster* StSstClusterList::next(StSstCluster *ptr)
54 { return ptr->getNextCluster(); }
55 
56 StSstCluster* StSstClusterList::prev(StSstCluster *ptr)
57 { return ptr->getPrevCluster(); }
58 
59 StSstCluster* StSstClusterList::first()
60 { return mFirstCluster; }
61 
62 StSstCluster* StSstClusterList::last()
63 { return mLastCluster; }
64 
65 Int_t StSstClusterList::addNewCluster(StSstCluster *ptr)
66 {
67  if (!ptr) return 0;
68  if (mListLength == 0)
69  {
70  ptr->setPrevCluster(0);
71  ptr->setNextCluster(0);
72  mFirstCluster = ptr;
73  mLastCluster = ptr;
74  }
75  else
76  {
77  ptr->setPrevCluster(mLastCluster);
78  ptr->setNextCluster(0);
79  mLastCluster->setNextCluster(ptr);
80  mLastCluster = ptr;
81  }
82  mListLength++;
83  return 1;
84 }
85 
86 void StSstClusterList::exchangeTwoClusters(StSstCluster *ptr1,StSstCluster *ptr2)
87 {
88  StSstCluster *ptrTemp = new StSstCluster(ptr1->getNCluster());
89  ptr1->copyTo(ptrTemp);
90  ptr2->copyTo(ptr1);
91  ptrTemp->copyTo(ptr2);
92  delete ptrTemp;
93 }
94 
95 void StSstClusterList::sortCluster()
96 {
97  Int_t localSize=this->getSize();
98  if (localSize<2) return;
99 
100  StSstCluster *ptCurr = this->first();
101  ptCurr = this->next(ptCurr);
102  for ( ; ptCurr!=0 ; )
103  {
104  StSstCluster *ptB1 = ptCurr;
105  StSstCluster *ptB2;
106  Int_t isCont = 1;
107  while ((ptB1 != this->first())&&(isCont))
108  {
109  ptB2 = this->prev(ptB1);
110  if (ptB2->getFirstStrip() > ptB1->getFirstStrip())
111  {
112  this->exchangeTwoClusters(ptB1,ptB2);
113  ptB1 = ptB2;
114  }
115  else
116  {
117  isCont = 0;
118  }
119  }
120  ptCurr = this->next(ptCurr);
121 
122  }
123  return;
124 }
125 
126 void StSstClusterList::renumCluster()
127 {
128  Int_t CurrentListSize = this->getSize();
129  if (!CurrentListSize) return;
130  StSstCluster *CurrCluster = this->first();
131  for (Int_t i = 0; i < CurrentListSize; i++)
132  {
133  CurrCluster->setNCluster(i);
134  CurrCluster = this->next(CurrCluster);
135  }
136  return;
137 }
138 
139 Int_t StSstClusterList::removeCluster(StSstCluster *ptr)
140 {
141  if (!this->getSize()) return 0;
142  StSstCluster *ptBefore = ptr->getPrevCluster();
143  StSstCluster *ptAfter = ptr->getNextCluster();
144 
145  if (ptBefore == 0)
146  {
147  if (ptAfter== 0)
148  {
149  // taille = 1
150  this->mFirstCluster = 0;
151  this->mLastCluster = 0;
152  this->mListLength = 0;
153  delete ptr;
154  return 1;
155  }
156  else
157  {
158  this->mFirstCluster = ptAfter;
159  ptAfter->setPrevCluster(0);
160  this->mListLength--;
161  delete ptr;
162  return 1;
163  }
164  }
165  else
166  {
167  if (ptAfter== 0)
168  {
169  this->mLastCluster = ptBefore;
170  ptBefore->setNextCluster(0);
171  this->mListLength--;
172  delete ptr;
173  return 1;
174  }
175  else
176  {
177  ptBefore->setNextCluster(ptAfter);
178  ptAfter->setPrevCluster(ptBefore);
179  this->mListLength--;
180  delete ptr;
181  return 1;
182  }
183  }
184 }
185 
186 Int_t StSstClusterList::getSize()
187 { return mListLength; }
188 
189 Int_t StSstClusterList::splitCluster(StSstClusterControl *clusterControl, StSstCluster *CurrentCluster, Int_t *ListAdc, StSstStripList *currentStripList)
190 {
191  Int_t CurrentClusterSize = CurrentCluster->getClusterSize();
192  if (CurrentClusterSize<3) return 0;
193  Int_t nSubCluster = 0;
194  Int_t isClimbOrFall = 0;
195 
196  Float_t testTolerance = clusterControl->getTestTolerance();//20%
197  std::vector<int> minima(CurrentClusterSize,0);
198  std::vector<int> maxima(CurrentClusterSize,0);
199  std::vector<int> keyToIdStrip(CurrentClusterSize,0);
200  Int_t nMinima = 0;
201  Int_t nMaxima = 0;
202  Int_t iStrip = 0;
203 
204  keyToIdStrip[0] = CurrentCluster->getFirstStrip();
205 
206  for(iStrip = 1; iStrip<CurrentClusterSize; iStrip++)
207  {
208  keyToIdStrip[iStrip] = keyToIdStrip[iStrip-1]+1;
209  }
210 
211  iStrip = 0;
212 
213  for (iStrip = 0; iStrip<CurrentClusterSize-1; iStrip++) // we check both iStrip and iStrip+1
214  {
215  if (ListAdc[iStrip]<ListAdc[iStrip+1])
216  {
217  if ((isClimbOrFall == -1) || (isClimbOrFall == 0))
218  {
219  isClimbOrFall = 1;
220  minima[nMinima] = iStrip;
221  nMinima++;
222  }
223  if ((isClimbOrFall == 1) && (iStrip+2 == CurrentClusterSize))
224  {
225  maxima[nMaxima] = iStrip+1;
226  nMaxima++;
227  }
228  }
229  if (ListAdc[iStrip]>ListAdc[iStrip+1])
230  {
231  if ((isClimbOrFall == 1) || (isClimbOrFall == 0))
232  {
233  isClimbOrFall = -1;
234  maxima[nMaxima] = iStrip;
235  nMaxima++;
236  }
237  if ((isClimbOrFall == -1) && (iStrip+2 == CurrentClusterSize))
238  {
239  minima[nMinima] = iStrip+1;
240  nMinima++;
241  }
242  }
243  }
244 
245  if (nMaxima<2){
246  if(maxima.size()>0) maxima.clear();
247  if(minima.size()>0) minima.clear();
248  if(keyToIdStrip.size()>0) keyToIdStrip.clear();
249  return 0;
250  }
251  Int_t iMaxima = 0;
252  Int_t maxLeft = 0;
253  Int_t maxRight =0;
254  Int_t localFirstStrip = CurrentCluster->getFirstStrip();
255  Float_t weight = 1.;
256  Int_t strip_offset = 0;//JB : 01/08/2007 : update the current strip when the splitting of clusters is done
257  Int_t strip_diff = 0;
258  for (iMaxima = 0; iMaxima<nMaxima-1 ; iMaxima++)
259  {
260  maxLeft = maxima[iMaxima];
261  maxRight = maxima[iMaxima+1];
262  Int_t iMinima = 0;
263  while (!(minima[iMinima]>maxLeft && minima[iMinima]<maxRight) && iMinima<nMinima) iMinima++;
264 
265  if (iMinima == nMinima)
266  {
267  cout<<"Big Bug in StSstClusterList -> I do not find any minima between the two maxima !"<<endl;
268  return 0;
269  }
270 
271  // process strip in the Left direction
272  Int_t theEnd = 0;
273  Int_t iStripLeft = minima[iMinima]-1;
274  Int_t iStripRight = minima[iMinima]+1;
275  Int_t iSuccess = 1;
276  Int_t addLeft = 0;
277  Int_t addRight = 0;
278  Int_t nStripInTheGroup = 1;
279  Float_t meanAdc = (float)ListAdc[minima[iMinima]];
280  localFirstStrip = CurrentCluster->getFirstStrip()+strip_offset;
281  weight = 1.;
282 
283  while(!theEnd)
284  {
285  if (fabs(((float)ListAdc[iStripLeft]-meanAdc)/meanAdc)<testTolerance)
286  {
287  if (iStripLeft > maxLeft)
288  {
289  addLeft = 1;
290  }
291  else
292  {
293  theEnd = 1;
294  iSuccess = 0;
295  }
296  }
297  if (fabs(((float)ListAdc[iStripRight]-meanAdc)/meanAdc)<testTolerance)
298  {
299  if (iStripRight < maxRight)
300  {
301  addRight = 1;
302  }
303  else
304  {
305  theEnd = 1;
306  iSuccess = 0;
307  }
308  }
309 
310  if ((!addLeft)&&(!addRight)) theEnd =1;
311  if (addLeft)
312  {
313  meanAdc = (((float)nStripInTheGroup)*meanAdc + (float)ListAdc[iStripLeft])/((float)(nStripInTheGroup+1));
314  nStripInTheGroup++;
315  iStripLeft--;
316  addLeft = 0;
317  }
318  if (addRight)
319  {
320  meanAdc = (((float)nStripInTheGroup)*meanAdc + (float)ListAdc[iStripRight])/((float)(nStripInTheGroup+1));
321  nStripInTheGroup++;
322  iStripRight++;
323  addRight = 0;
324  }
325  }
326 
327  if (iSuccess)
328  {
329  if (nStripInTheGroup%2==0)
330  {
331  StSstCluster *newCluster = new StSstCluster(this->getSize());
332  newCluster->setFlag(1);
333  Int_t currentStrip = localFirstStrip;
334  for (currentStrip = localFirstStrip; currentStrip<=(keyToIdStrip[iStripLeft]+(nStripInTheGroup/2)); currentStrip++)
335  {
336  newCluster->update(currentStripList->getStrip(currentStrip),weight);
337  weight=1.;
338  localFirstStrip=currentStrip+1;
339  strip_diff++;
340  }
341  this->addNewCluster(newCluster);
342  }
343  else
344  {
345  StSstCluster *newCluster = new StSstCluster(this->getSize());
346  newCluster->setFlag(1);
347  Int_t currentStrip = localFirstStrip;
348  for (currentStrip = localFirstStrip; currentStrip<=(keyToIdStrip[iStripLeft]+(int)(nStripInTheGroup/2)); currentStrip++)
349  {
350  newCluster->update(currentStripList->getStrip(currentStrip),weight);
351  weight=1.;
352  localFirstStrip=currentStrip+1;
353  strip_diff++;
354  }
355  weight=0.5;
356  newCluster->update(currentStripList->getStrip(localFirstStrip),weight);//last strip
357  this->addNewCluster(newCluster);
358  }
359  nSubCluster++;
360  }
361  strip_offset = strip_diff;
362  }
363 
364  if(nSubCluster)
365  {
366  StSstCluster *newCluster = new StSstCluster(this->getSize());
367  newCluster->setFlag(1);
368  Int_t currentStrip = localFirstStrip;
369  for (currentStrip = localFirstStrip; currentStrip<(CurrentCluster->getFirstStrip()+CurrentCluster->getClusterSize()); currentStrip++)
370  {
371  newCluster->update(currentStripList->getStrip(currentStrip),weight);
372  weight=1.;
373  }
374  this->addNewCluster(newCluster);
375  nSubCluster++;
376  }
377  if(maxima.size()>0) maxima.clear();
378  if(minima.size()>0) minima.clear();
379  if(keyToIdStrip.size()>0) keyToIdStrip.clear();
380 
381  return nSubCluster;
382 }
383 
384 Int_t StSstClusterList::isSorted()
385 {
386  StSstCluster *ptr1 = this->first();
387  StSstCluster *ptr2 = 0;
388 
389  while(ptr1 != this->last())
390  {
391  ptr2 = this->next(ptr1);
392  if (ptr1->getFirstStrip()>ptr2->getFirstStrip()) return 0;
393  ptr1 = this->next(ptr1);
394  }
395  return 1;
396 }
397 
398 StSstClusterList::StSstClusterList(const StSstClusterList & originalClusterList)
399 {
400  mListLength = originalClusterList.mListLength;
401  mFirstCluster = originalClusterList.mFirstCluster;
402  mLastCluster = originalClusterList.mLastCluster;
403 }
404 
405 StSstClusterList& StSstClusterList::operator=(const StSstClusterList originalClusterList)
406 {
407  mListLength = originalClusterList.mListLength;
408  mFirstCluster = originalClusterList.mFirstCluster;
409  mLastCluster = originalClusterList.mLastCluster;
410 
411  return *this;
412 }