Analysis Software
Documentation for sPHENIX simulation software
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
SeedingFTFAlgorithm.cpp
Go to the documentation of this file. Or view the newest version in sPHENIX GitHub for file SeedingFTFAlgorithm.cpp
1 // This file is part of the Acts project.
2 //
3 // Copyright (C) 2020 CERN for the benefit of the Acts project
4 //
5 // This Source Code Form is subject to the terms of the Mozilla Public
6 // License, v. 2.0. If a copy of the MPL was not distributed with this
7 // file, You can obtain one at http://mozilla.org/MPL/2.0/.
8 
10 
12 #include "Acts/Seeding/Seed.hpp"
19 
20 #include <fstream>
21 #include <iostream>
22 #include <map>
23 #include <random>
24 #include <sstream>
25 #include <vector>
26 
27 using namespace std;
28 
36 
37 // constructor:
40  : ActsExamples::IAlgorithm("SeedingAlgorithm", lvl), m_cfg(std::move(cfg)) {
41  // fill config struct
43 
45 
48 
52 
53  for (const auto &spName : m_cfg.inputSpacePoints) {
54  if (spName.empty()) {
55  throw std::invalid_argument("Invalid space point input collection");
56  }
57 
58  auto &handle = m_inputSpacePoints.emplace_back(
60  this,
61  "InputSpacePoints#" + std::to_string(m_inputSpacePoints.size())));
62  handle->initialize(spName);
63  }
64 
66 
68 
70  std::make_unique<Acts::SeedFilter<SimSpacePoint>>(
72 
73  // map
75  // input trig vector
77 
78  std::ifstream input_ifstream(
80 
81  // fastrack
82  std::unique_ptr<Acts::FasTrackConnector> input_fastrack =
83  std::make_unique<Acts::FasTrackConnector>(input_ifstream);
84 
85  mGNNgeo = std::make_unique<Acts::TrigFTF_GNN_Geometry<SimSpacePoint>>(
86  m_cfg.seedFinderConfig.m_layerGeometry, input_fastrack);
87 
88 } // this is not FTF config type because it is a member of the algs config,
89  // which is of type FTF cofig
90 
91 // execute:
93  const AlgorithmContext &ctx) const {
94  std::vector<Acts::FTF_SP<SimSpacePoint>> FTF_spacePoints =
95  Make_FTF_spacePoints(ctx, m_cfg.ACTS_FTF_Map);
96 
97  for (auto sp : FTF_spacePoints) {
98  ACTS_DEBUG("FTF space points: "
99  << " FTF_id: " << sp.FTF_ID << " z: " << sp.SP->z()
100  << " r: " << sp.SP->r() << " ACTS volume: "
101  << sp.SP->sourceLinks()
102  .front()
103  .get<IndexSourceLink>()
104  .geometryId()
105  .volume()
106  << "\n");
107  }
108 
109  // this is now calling on a core algorithm
110  Acts::SeedFinderFTF<SimSpacePoint> finder(m_cfg.seedFinderConfig, *mGNNgeo);
111 
112  // need this function as create_coords is needed for seeds
113  std::function<std::pair<Acts::Vector3, Acts::Vector2>(
114  const SimSpacePoint *sp)>
115  create_coordinates = [](const SimSpacePoint *sp) {
116  Acts::Vector3 position(sp->x(), sp->y(), sp->z());
117  Acts::Vector2 variance(sp->varianceR(), sp->varianceZ());
118  return std::make_pair(position, variance);
119  };
120  // output of function needed for seed
121 
122  finder.loadSpacePoints(FTF_spacePoints);
123 
124  Acts::RoiDescriptor internalRoi(0, -4.5, 4.5, 0, -M_PI, M_PI, 0, -150.0,
125  150.0);
126 
127  finder.createSeeds(internalRoi, *mGNNgeo);
128 
129  // still to develop
130  SimSeedContainer seeds = finder.createSeeds_old(
131  m_cfg.seedFinderOptions, FTF_spacePoints, create_coordinates);
132 
133  m_outputSeeds(ctx, std::move(seeds));
134 
136 }
137 
138 std::map<std::pair<int, int>, std::pair<int, int>>
140  map<std::pair<int, int>, std::pair<int, int>> ACTS_FTF;
141  std::ifstream data(
142  m_cfg.layerMappingFile); // 0 in this file refers to no FTF ID
144  std::vector<std::vector<std::string>> parsedCsv;
145  while (std::getline(data, line)) {
146  std::stringstream lineStream(line);
147  std::string cell;
148  std::vector<std::string> parsedRow;
149  while (std::getline(lineStream, cell, ',')) {
150  parsedRow.push_back(cell);
151  }
152 
153  parsedCsv.push_back(parsedRow);
154  }
155  // file in format ACTS_vol,ACTS_lay,ACTS_mod,FTF_id
156  for (auto i : parsedCsv) {
157  int ACTS_vol = stoi(i[0]);
158  int ACTS_lay = stoi(i[1]);
159  int ACTS_mod = stoi(i[2]);
160  int FTF = stoi(i[5]);
161  int eta_mod = stoi(i[6]);
162  int ACTS_joint = ACTS_vol * 100 + ACTS_lay;
163  ACTS_FTF.insert({{ACTS_joint, ACTS_mod}, {FTF, eta_mod}});
164  }
165 
166  return ACTS_FTF;
167 }
168 
169 std::vector<Acts::FTF_SP<ActsExamples::SimSpacePoint>>
171  const AlgorithmContext &ctx,
172  std::map<std::pair<int, int>, std::pair<int, int>> map) const {
173  // create space point vectors
174  std::vector<const ActsExamples::SimSpacePoint *> spacePoints;
175  std::vector<Acts::FTF_SP<ActsExamples::SimSpacePoint>> FTF_spacePoints;
176  FTF_spacePoints.reserve(
177  m_inputSpacePoints.size()); // not sure if this is enough
178 
179  // for loop filling space
180  for (const auto &isp : m_inputSpacePoints) {
181  for (const auto &spacePoint : (*isp)(ctx)) {
182  // fill original space point vector
183  spacePoints.push_back(&spacePoint);
184 
185  // FTF space point vector
186  // loop over space points, call on map
187  const auto &source_link = spacePoint.sourceLinks();
188  const auto &index_source_link =
189  source_link.front().get<IndexSourceLink>();
190 
191  // warning if source link empty
192  if (source_link.empty()) {
193  // warning in officaial acts format
194  ACTS_WARNING("warning source link vector is empty");
195  continue;
196  }
197  int ACTS_vol_id = index_source_link.geometryId().volume();
198  int ACTS_lay_id = index_source_link.geometryId().layer();
199  int ACTS_mod_id = index_source_link.geometryId().sensitive();
200 
201  // dont want strips or HGTD
202  if (ACTS_vol_id == 2 or ACTS_vol_id == 22 or ACTS_vol_id == 23 or
203  ACTS_vol_id == 24) {
204  continue;
205  }
206 
207  // Search for vol, lay and module=0, if doesn't esist (end) then search
208  // for full thing vol*100+lay as first number in pair then 0 or mod id
209  auto ACTS_joint_id = ACTS_vol_id * 100 + ACTS_lay_id;
210  auto key = std::make_pair(
211  ACTS_joint_id,
212  0); // here the key needs to be pair of(vol*100+lay, 0)
213  auto Find = map.find(key);
214 
215  if (Find ==
216  map.end()) { // if end then make new key of (vol*100+lay, modid)
217  key = std::make_pair(ACTS_joint_id, ACTS_mod_id); // mod ID
218  Find = map.find(key);
219  }
220 
221  // warning if key not in map
222  if (Find == map.end()) {
223  ACTS_WARNING("Key not found in FTF map for volume id: "
224  << ACTS_vol_id << " and layer id: " << ACTS_lay_id);
225  continue;
226  }
227 
228  // now should be pixel with FTF ID:
229  int FTF_id =
230  Find->second
231  .first; // new map the item is a pair so want first from it
232 
233  if (FTF_id == 0) {
234  ACTS_WARNING("No assigned FTF ID for key for volume id: "
235  << ACTS_vol_id << " and layer id: " << ACTS_lay_id);
236  }
237 
238  // access IDs from map
239  int eta_mod = Find->second.second;
240  int combined_id = FTF_id * 1000 + eta_mod;
241 
242  // fill FTF vector with current sapce point and ID
243  FTF_spacePoints.emplace_back(&spacePoint, FTF_id, combined_id);
244  }
245  }
246  ACTS_VERBOSE("Space points successfully assigned FTF ID");
247 
248  return FTF_spacePoints;
249 }
250 
251 std::vector<Acts::TrigInDetSiLayer>
253  std::vector<Acts::TrigInDetSiLayer> input_vector;
254  std::vector<size_t> count_vector;
255 
256  m_cfg.trackingGeometry->visitSurfaces([this, &input_vector, &count_vector](
257  const Acts::Surface *surface) {
258  Acts::GeometryIdentifier geoid = surface->geometryId();
259  auto ACTS_vol_id = geoid.volume();
260  auto ACTS_lay_id = geoid.layer();
261  auto mod_id = geoid.sensitive();
262  auto bounds_vect = surface->bounds().values();
263  auto center = surface->center(Acts::GeometryContext());
264 
265  // make bounds global
266  Acts::Vector3 globalFakeMom(1, 1, 1);
267  Acts::Vector2 min_bound_local =
268  Acts::Vector2(bounds_vect[0], bounds_vect[1]);
269  Acts::Vector2 max_bound_local =
270  Acts::Vector2(bounds_vect[2], bounds_vect[3]);
271  Acts::Vector3 min_bound_global = surface->localToGlobal(
272  Acts::GeometryContext(), min_bound_local, globalFakeMom);
273  Acts::Vector3 max_bound_global = surface->localToGlobal(
274  Acts::GeometryContext(), max_bound_local, globalFakeMom);
275 
276  if (min_bound_global(0) >
277  max_bound_global(0)) { // checking that not wrong way round
278  min_bound_global.swap(max_bound_global);
279  }
280 
281  float rc = 0.0;
282  float minBound = 100000.0;
283  float maxBound = -100000.0;
284 
285  // convert to FTF ID
286  auto ACTS_joint_id = ACTS_vol_id * 100 + ACTS_lay_id;
287  auto key =
288  std::make_pair(ACTS_joint_id,
289  0); // here the key needs to be pair of(vol*100+lay, 0)
290  auto Find = m_cfg.ACTS_FTF_Map.find(key);
291  int FTF_id = Find->second.first; // new map, item is pair want first
292  if (Find ==
293  m_cfg.ACTS_FTF_Map
294  .end()) { // if end then make new key of (vol*100+lay, modid)
295  key = std::make_pair(ACTS_joint_id, mod_id); // mod ID
296  Find = m_cfg.ACTS_FTF_Map.find(key);
297  FTF_id = Find->second.first;
298  }
299 
300  short barrel_ec = 0; // a variable that says if barrrel, 0 = barrel
301  int eta_mod = Find->second.second;
302 
303  // assign barrel_ec depending on FTF_layer
304  if (79 < FTF_id && FTF_id < 85) { // 80s, barrel
305  barrel_ec = 0;
306  } else if (89 < FTF_id && FTF_id < 99) { // 90s positive
307  barrel_ec = 2;
308  } else { // 70s negative
309  barrel_ec = -2;
310  }
311 
312  if (barrel_ec == 0) {
313  rc = sqrt(center(0) * center(0) +
314  center(1) * center(1)); // barrel center in r
315  // bounds of z
316  if (min_bound_global(2) < minBound) {
317  minBound = min_bound_global(2);
318  }
319  if (max_bound_global(2) > maxBound) {
320  maxBound = max_bound_global(2);
321  }
322  } else {
323  rc = center(2); // not barrel center in Z
324  // bounds of r
325  float min = sqrt(min_bound_global(0) * min_bound_global(0) +
326  min_bound_global(1) * min_bound_global(1));
327  float max = sqrt(max_bound_global(0) * max_bound_global(0) +
328  max_bound_global(1) * max_bound_global(1));
329  if (min < minBound) {
330  minBound = min;
331  }
332  if (max > maxBound) {
333  maxBound = max;
334  }
335  }
336 
337  int combined_id = FTF_id * 1000 + eta_mod;
338  auto current_index =
339  find_if(input_vector.begin(), input_vector.end(),
340  [combined_id](auto n) { return n.m_subdet == combined_id; });
341  if (current_index != input_vector.end()) { // not end so does exist
342  size_t index = std::distance(input_vector.begin(), current_index);
343  input_vector[index].m_refCoord += rc;
344  input_vector[index].m_minBound += minBound;
345  input_vector[index].m_maxBound += maxBound;
346  count_vector[index] += 1; // increase count at the index
347 
348  } else { // end so doesn't exists
349  // make new if one with FTF ID doesn't exist:
350  Acts::TrigInDetSiLayer new_FTF_ID(combined_id, barrel_ec, rc, minBound,
351  maxBound);
352  input_vector.push_back(new_FTF_ID);
353  count_vector.push_back(
354  1); // so the element exists and not divinding by 0
355  }
356 
357  if (m_cfg.fill_module_csv) {
358  fstream fout;
359  fout.open("ACTS_modules.csv",
360  ios::out | ios::app); // add to file each time
361  // print to csv for each module, no repeats so dont need to make
362  // map for averaging
363  fout << ACTS_vol_id << ", " // vol
364  << ACTS_lay_id << ", " // lay
365  << mod_id << ", " // module
366  << FTF_id << "," // FTF id
367  << eta_mod << "," // eta_mod
368  << center(2) << ", " // z
369  << sqrt(center(0) * center(0) + center(1) * center(1)) // r
370  << "\n";
371  }
372  });
373 
374  for (long unsigned int i = 0; i < input_vector.size(); i++) {
375  input_vector[i].m_refCoord = input_vector[i].m_refCoord / count_vector[i];
376  }
377 
378  return input_vector;
379 }