Analysis Software
Documentation for sPHENIX simulation software
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
RawClusterPositionCorrection.cc
Go to the documentation of this file. Or view the newest version in sPHENIX GitHub for file RawClusterPositionCorrection.cc
2 
3 #include <calobase/RawCluster.h>
4 #include <calobase/RawClusterContainer.h>
5 #include <calobase/RawClusterUtility.h>
6 #include <calobase/RawTower.h>
7 #include <calobase/RawTowerContainer.h>
8 #include <calobase/RawTowerDefs.h> // for decode_index1, decode_in...
9 #include <calobase/RawTowerGeomContainer.h>
10 #include <calobase/TowerInfo.h>
11 #include <calobase/TowerInfoContainer.h>
12 
13 #include <cdbobjects/CDBHistos.h> // for CDBHistos
14 #include <cdbobjects/CDBTTree.h> // for CDBTTree
15 
17 
18 #include <phparameter/PHParameters.h>
19 
21 #include <fun4all/SubsysReco.h>
22 
23 #include <phool/PHCompositeNode.h>
24 #include <phool/PHIODataNode.h>
25 #include <phool/PHNode.h>
26 #include <phool/PHNodeIterator.h>
27 #include <phool/PHObject.h>
28 #include <phool/getClass.h>
29 #include <phool/phool.h>
30 
31 #include <TH1.h>
32 #include <TH2.h>
33 #include <TSystem.h>
34 
35 #include <algorithm> // for max
36 
37 #include <cassert>
38 #include <cmath>
39 #include <fstream>
40 #include <iostream>
41 #include <map>
42 #include <sstream>
43 #include <stdexcept>
44 #include <string>
45 #include <utility> // for pair
46 
48  : SubsysReco(std::string("RawClusterPositionCorrection_") + name)
49  , _det_name(name)
50  , bins_eta(384)
51  , bins_phi(64)
52  , iEvent(0)
53 {
54 }
56 {
57  delete cdbHisto;
58  delete cdbttree;
59 }
60 
62 {
63  CreateNodeTree(topNode);
64 
65  // access the cdb and get cdbtree
66  std::string m_calibName = "cemc_PDC_NorthSouth_8x8_23instru";
67  std::string calibdir = CDBInterface::instance()->getUrl(m_calibName);
68  if (!calibdir.empty())
69  {
70  cdbttree = new CDBTTree(calibdir);
71  }
72  else
73  {
74  std::cout << std::endl
75  << "did not find CDB tree" << std::endl;
76  gSystem->Exit(1);
77  exit(1);
78  }
79 
80  h2NorthSector = new TH2F("h2NorthSector", "Cluster; towerid #eta; towerid #phi", bins_eta, 47.5, 95.5, bins_phi, -0.5, 7.5);
81  h2SouthSector = new TH2F("h2SouthSector", "Cluster; towerid #eta; towerid #phi", bins_eta, -0.5, 47.5, bins_phi, -0.5, 7.5);
82 
84  std::string m_fieldname = "cemc_PDC_NorthSector_8x8_clusE";
85  std::string m_fieldname_ecore = "cemc_PDC_NorthSector_8x8_clusEcore";
86  float calib_constant = 0;
87 
88  // Read in the calibration factors and store in the array
89  for (int i = 0; i < bins_phi; ++i)
90  {
91  std::vector<float> dumvec;
92  std::vector<float> dumvec2;
93  for (int j = 0; j < bins_eta; ++j)
94  {
95  int key = i * bins_eta + j;
96  calib_constant = cdbttree->GetFloatValue(key, m_fieldname);
97  dumvec.push_back(calib_constant);
98  calib_constant = cdbttree->GetFloatValue(key, m_fieldname_ecore);
99  dumvec2.push_back(calib_constant);
100  }
101  calib_constants_north.push_back(dumvec);
102  calib_constants_north_ecore.push_back(dumvec2);
103  }
105  m_fieldname = "cemc_PDC_SouthSector_8x8_clusE";
106  m_fieldname_ecore = "cemc_PDC_SouthSector_8x8_clusEcore";
107 
108  // Read in the calibration factors and store in the array
109  for (int i = 0; i < bins_phi; ++i)
110  {
111  std::vector<float> dumvec;
112  std::vector<float> dumvec2;
113  for (int j = 0; j < bins_eta; ++j)
114  {
115  int key = i * bins_eta + j;
116  calib_constant = cdbttree->GetFloatValue(key, m_fieldname);
117  dumvec.push_back(calib_constant);
118  calib_constant = cdbttree->GetFloatValue(key, m_fieldname_ecore);
119  dumvec2.push_back(calib_constant);
120  }
121  calib_constants_south.push_back(dumvec);
122  calib_constants_south_ecore.push_back(dumvec2);
123  }
124 
125  // Load PDC final stage correction
126  calibdir = CDBInterface::instance()->getUrl("cemc_PDC_ResidualCorr");
127  if (!calibdir.empty())
128  {
129  cdbHisto = new CDBHistos(calibdir.c_str());
131  //pdcCorrFlat = cdbHisto->getHisto("h1_res_p");
132  pdcCorrFlat = cdbHisto->getHisto("h_res_E_eta");
133  }
134  else
135  {
136  std::cout << std::endl
137  << "did not find CDB histo" << std::endl;
138  gSystem->Exit(1);
139  exit(1);
140  }
142 }
143 
145 {
146  // make sure new cluster container is empty
148 
150  {
151  if (iEvent % 100 == 0) std::cout << "Progress: " << iEvent << std::endl;
152  ++iEvent;
153  }
154 
155  std::string rawClusNodeName = "CLUSTER_" + _det_name;
156  if (m_UseTowerInfo)
157  {
158  rawClusNodeName = "CLUSTERINFO_" + _det_name;
159  }
160 
161  RawClusterContainer *rawclusters = findNode::getClass<RawClusterContainer>(topNode, rawClusNodeName.c_str());
162  if (!rawclusters)
163  {
164  std::cout << "No " << _det_name << " Cluster Container found while in RawClusterPositionCorrection, can't proceed!!!" << std::endl;
166  }
167 
168  RawTowerContainer *_towers = nullptr;
169  TowerInfoContainer *_towerinfos = nullptr;
170 
171  if (!m_UseTowerInfo)
172  {
173  _towers = findNode::getClass<RawTowerContainer>(topNode, "TOWER_CALIB_" + _det_name);
174  if (!_towers)
175  {
176  std::cout << "No calibrated " << _det_name << " tower info found while in RawClusterPositionCorrection, can't proceed!!!" << std::endl;
178  }
179  }
180  else
181  {
182  std::string towerinfoNodename = "TOWERINFO_CALIB_" + _det_name;
183 
184  _towerinfos = findNode::getClass<TowerInfoContainer>(topNode, towerinfoNodename);
185  if (!_towerinfos)
186  {
187  std::cerr << Name() << "::" << _det_name << "::" << __PRETTY_FUNCTION__
188  << " " << towerinfoNodename << " Node missing, doing bail out!"
189  << std::endl;
190 
192  }
193  }
194 
195  std::string towergeomnodename = "TOWERGEOM_" + _det_name;
196  RawTowerGeomContainer *towergeom = findNode::getClass<RawTowerGeomContainer>(topNode, towergeomnodename);
197  if (!towergeom)
198  {
199  std::cout << PHWHERE << ": Could not find node " << towergeomnodename << std::endl;
201  }
202  const int nphibin = towergeom->get_phibins();
203 
204  // loop over the clusters
205  RawClusterContainer::ConstRange begin_end = rawclusters->getClusters();
207 
208  for (iter = begin_end.first; iter != begin_end.second; ++iter)
209  {
210  // RawClusterDefs::keytype key = iter->first;
211  RawCluster *cluster = iter->second;
212 
213  float clus_energy = cluster->get_energy();
214 
215  std::vector<float> toweretas;
216  std::vector<float> towerphis;
217  std::vector<float> towerenergies;
218 
219  // loop over the towers in the cluster
220  RawCluster::TowerConstRange towers = cluster->get_towers();
222  for (toweriter = towers.first;
223  toweriter != towers.second;
224  ++toweriter)
225  {
226  if (!m_UseTowerInfo)
227  {
228  RawTower *tower = _towers->getTower(toweriter->first);
229 
230  int towereta = tower->get_bineta();
231  int towerphi = tower->get_binphi();
232  double towerenergy = tower->get_energy();
233 
234  // put the etabin, phibin, and energy into the corresponding vectors
235  toweretas.push_back(towereta);
236  towerphis.push_back(towerphi);
237  towerenergies.push_back(towerenergy);
238  }
239  else
240  {
241  // std::cout << "clus " << iter->first << " tow key " << toweriter->first << " decoded to " << towerindex << std::endl;
242 
243  int iphi = RawTowerDefs::decode_index2(toweriter->first); // index2 is phi in CYL
244  int ieta = RawTowerDefs::decode_index1(toweriter->first); // index1 is eta in CYL
245  unsigned int towerkey = iphi + (ieta << 16U);
246 
247  assert(_towerinfos);
248 
249  unsigned int towerindex = _towerinfos->decode_key(towerkey);
250 
251  TowerInfo *towinfo = _towerinfos->get_tower_at_channel(towerindex);
252 
253  double towerenergy = towinfo->get_energy();
254 
255  // put the eta, phi, energy into corresponding vectors
256  toweretas.push_back(ieta);
257  towerphis.push_back(iphi);
258  towerenergies.push_back(towerenergy);
259  }
260  }
261 
262  int ntowers = toweretas.size();
263  // std::cout << "jf " << ntowers << std::endl;
264  assert(ntowers >= 1);
265 
266  // loop over the towers to determine the energy
267  // weighted eta and phi position of the cluster
268 
269  float etamult = 0;
270  float etasum = 0;
271  float phimult = 0;
272  float phisum = 0;
273 
274  for (int j = 0; j < ntowers; j++)
275  {
276  float energymult = towerenergies.at(j) * toweretas.at(j);
277  etamult += energymult;
278  etasum += towerenergies.at(j);
279 
280  int phibin = towerphis.at(j);
281 
282  if (phibin - towerphis.at(0) < -nphibin / 2.0)
283  {
284  phibin += nphibin;
285  }
286  else if (phibin - towerphis.at(0) > +nphibin / 2.0)
287  {
288  phibin -= nphibin;
289  }
290  assert(std::abs(phibin - towerphis.at(0)) <= nphibin / 2.0);
291 
292  energymult = towerenergies.at(j) * phibin;
293  phimult += energymult;
294  phisum += towerenergies.at(j);
295  }
296 
297  float avgphi = phimult / phisum;
298  if (isnan(avgphi)) continue;
299 
300  float avgeta = etamult / etasum;
301 
302  if (avgphi < 0)
303  {
304  avgphi += nphibin;
305  }
306 
307  avgphi = fmod(avgphi, nphibin);
308 
309  if (avgphi >= 255.5) avgphi -= bins_phi;
310 
311  avgphi = fmod(avgphi + 0.5, 8) - 0.5; // wrapping [-0.5, 255.5] to [-0.5, 7.5]
312  int etabin = -99;
313  int phibin = -99;
314 
315  // check if the cluster is in the north or south sector
316  if (avgeta < 47.5)
317  {
318  etabin = h2SouthSector->GetXaxis()->FindBin(avgeta) - 1;
319  }
320  else
321  {
322  etabin = h2NorthSector->GetXaxis()->FindBin(avgeta) - 1;
323  }
324  phibin = h2NorthSector->GetYaxis()->FindBin(avgphi) - 1; // can use either h2NorthSector or h2SouthSector since both have the same phi binning
325 
326  if ((phibin < 0 || etabin < 0) && Verbosity() >= Fun4AllBase::VERBOSITY_MORE)
327  {
328  std::cout << "couldn't recalibrate cluster, something went wrong??" << std::endl;
329  }
330 
331  float eclus_recalib_val = 1;
332  float ecore_recalib_val = 1;
333  if (phibin > -1 && etabin > -1)
334  {
335  if (avgeta < 47.5)
336  {
337  eclus_recalib_val = calib_constants_south[phibin][etabin];
338  ecore_recalib_val = calib_constants_south_ecore[phibin][etabin];
339  }
340  else
341  {
342  eclus_recalib_val = calib_constants_north[phibin][etabin];
343  ecore_recalib_val = calib_constants_north_ecore[phibin][etabin];
344  }
345  }
346  RawCluster *recalibcluster = dynamic_cast<RawCluster *>(cluster->CloneMe());
347 
348  assert(recalibcluster);
349  // if (m_UseTowerInfo)
350  recalibcluster->set_energy(clus_energy / eclus_recalib_val);
351  recalibcluster->set_ecore(cluster->get_ecore() / ecore_recalib_val);
352 
353  CLHEP::Hep3Vector vertex(0,0,0);
354  CLHEP::Hep3Vector E_vec_cluster = RawClusterUtility::GetECoreVec(*recalibcluster, vertex);
355  float clusEta = E_vec_cluster.pseudoRapidity();
356 
357  if (cluster->get_ecore() >= pdcCorrFlat->GetXaxis()->GetXmin()
358  && cluster->get_ecore() < pdcCorrFlat->GetXaxis()->GetXmax()
359  && clusEta >= pdcCorrFlat->GetYaxis()->GetXmin()
360  && clusEta < pdcCorrFlat->GetYaxis()->GetXmax()
361  )
362  {
363 
364  int ecoreBin = pdcCorrFlat->GetXaxis()->FindBin(recalibcluster->get_ecore());
365  int etaBin = pdcCorrFlat -> GetYaxis() -> FindBin(clusEta);
366  float pdcCalib = pdcCorrFlat -> GetBinContent(ecoreBin, etaBin);
367  //float pdcCalib = pdcCorrFlat->GetBinContent(ecoreBin);
368  if (pdcCalib < 0.1) pdcCalib = 1;
369 
370  recalibcluster->set_ecore(recalibcluster->get_ecore() / pdcCalib);
371  }
372 
373  _recalib_clusters->AddCluster(recalibcluster);
374 
375  if (Verbosity() >= Fun4AllBase::VERBOSITY_EVEN_MORE && clus_energy > 1)
376  {
377  std::cout << "Input eclus cluster energy: " << clus_energy << std::endl;
378  std::cout << "Recalib value: " << eclus_recalib_val << std::endl;
379  std::cout << "phibin: " << phibin << ", etabin: " << etabin << std::endl;
380  std::cout << "Recalibrated eclus cluster energy: "
381  << clus_energy / eclus_recalib_val << std::endl;
382  std::cout << "Input ecore cluster energy: "
383  << cluster->get_ecore() << std::endl;
384  std::cout << "Recalib value: " << ecore_recalib_val << std::endl;
385  std::cout << "Recalibrated ecore cluster energy: "
386  << cluster->get_ecore() / ecore_recalib_val << std::endl;
387  }
388  }
389 
391 }
392 
393 
395 {
396  PHNodeIterator iter(topNode);
397 
398  // Get the DST Node
399  PHCompositeNode *dstNode = dynamic_cast<PHCompositeNode *>(iter.findFirst("PHCompositeNode", "DST"));
400 
401  // Check that it is there
402  if (!dstNode)
403  {
404  std::cout << "DST Node missing, quitting" << std::endl;
405  throw std::runtime_error("failed to find DST node in RawClusterPositionCorrection::CreateNodeTree");
406  }
407 
408  // Get the _det_name subnode
409  PHCompositeNode *cemcNode = dynamic_cast<PHCompositeNode *>(iter.findFirst("PHCompositeNode", _det_name));
410 
411  // Check that it is there
412  if (!cemcNode)
413  {
414  cemcNode = new PHCompositeNode(_det_name);
415  dstNode->addNode(cemcNode);
416  }
417 
418  // Check to see if the cluster recalib node is on the nodetree
419  std::string ClusterCorrNodeName = "CLUSTER_POS_COR_" + _det_name;
420  if (m_UseTowerInfo)
421  {
422  ClusterCorrNodeName = "CLUSTERINFO_POS_COR_" + _det_name;
423  }
424  _recalib_clusters = findNode::getClass<RawClusterContainer>(topNode, ClusterCorrNodeName);
425  if (_recalib_clusters)
426  {
427  _recalib_clusters->Clear();
428  }
429  else
430  {
432  PHIODataNode<PHObject> *clusterNode = new PHIODataNode<PHObject>(_recalib_clusters, ClusterCorrNodeName, "PHObject");
433  cemcNode->addNode(clusterNode);
434  }
435 }
437 {
439 }