160 gsl::span<const DigROFRecord> digitROFs,
161 std::vector<o2::trkft3::TRKCluster>&
clusters,
162 std::vector<unsigned char>& patterns,
163 std::vector<o2::trkft3::ROFRecord>& clusterROFs,
168 mThread = std::make_unique<ClustererThread>(
this);
173 for (
size_t iROF = 0; iROF < digitROFs.size(); ++iROF) {
174 const auto& inROF = digitROFs[iROF];
175 const auto outFirst =
static_cast<int>(
clusters.size());
176 const int first = inROF.getFirstEntry();
177 const int nEntries = inROF.getNEntries();
180 clusterROFs.emplace_back(inROF.getBCData(), inROF.getROFrame(), outFirst, 0);
189 const auto& da = digits[a];
190 const auto& db = digits[b];
191 if (da.getChipIndex() != db.getChipIndex()) {
192 return da.getChipIndex() < db.getChipIndex();
194 if (da.getColumn() != db.getColumn()) {
195 return da.getColumn() < db.getColumn();
197 return da.getRow() < db.getRow();
202 using CellCollection = std::vector<Cell>;
204 using ClusterCollection = std::vector<Cluster>;
205 static constexpr int GridDim = 2;
207 CellCollection
cells;
208 Acts::Ccl::ClusteringData
data;
209 ClusterCollection clsCollection;
213 while (sliceStart < nEntries) {
214 const int chipFirst = sliceStart;
215 const uint16_t chipID =
digits[
mSortIdx[sliceStart]].getChipIndex();
216 while (sliceStart < nEntries &&
digits[
mSortIdx[sliceStart]].getChipIndex() == chipID) {
219 const int chipN = sliceStart - chipFirst;
224 clsCollection.clear();
225 cells.reserve(chipN);
226 for (
int i = chipFirst;
i < chipFirst + chipN; ++
i) {
228 cells.emplace_back(digit.getRow(), digit.getColumn(),
mSortIdx[
i]);
231 LOG(
debug) <<
"Clustering with ACTS on chip " << chipID <<
" " <<
cells.size() <<
" digits";
232 Acts::Ccl::createClusters<CellCollection, ClusterCollection, GridDim>(
data,
235 Acts::Ccl::DefaultConnect<Cell, GridDim>(
false));
237 LOG(
debug) <<
" found " << clsCollection.size() <<
" clusters";
240 for (
const auto& actsCluster : clsCollection) {
241 if (actsCluster.cells.empty()) {
246 uint16_t rowMin =
static_cast<uint16_t
>(actsCluster.cells[0].row);
247 uint16_t rowMax = rowMin;
248 uint16_t colMin =
static_cast<uint16_t
>(actsCluster.cells[0].col);
249 uint16_t colMax = colMin;
251 for (
const auto& cell : actsCluster.cells) {
252 rowMin = std::min(rowMin,
static_cast<uint16_t
>(cell.row));
253 rowMax = std::max(rowMax,
static_cast<uint16_t
>(cell.row));
254 colMin = std::min(colMin,
static_cast<uint16_t
>(cell.col));
255 colMax = std::max(colMax,
static_cast<uint16_t
>(cell.col));
258 const uint16_t rowSpan = rowMax - rowMin + 1;
259 const uint16_t colSpan = colMax - colMin + 1;
267 LOG(warning) <<
"Splitting huge TRK cluster: chipID " << chipID
268 <<
", rows " << rowMin <<
":" << rowMax
269 <<
" cols " << colMin <<
":" << colMax;
271 for (uint16_t tileColMin = colMin; tileColMin <= colMax;
275 for (uint16_t tileRowMin = rowMin; tileRowMin <= rowMax;
280 std::vector<std::pair<uint16_t, uint16_t>> tileCells;
281 for (
const auto& cell : actsCluster.cells) {
282 uint16_t
r =
static_cast<uint16_t
>(cell.row);
283 uint16_t
c =
static_cast<uint16_t
>(cell.col);
284 if (
r >= tileRowMin && r <= tileRowMax && c >= tileColMin &&
c <= tileColMax) {
285 tileCells.emplace_back(
r,
c);
289 if (tileCells.empty()) {
293 uint16_t tileRowSpan = tileRowMax - tileRowMin + 1;
294 uint16_t tileColSpan = tileColMax - tileColMin + 1;
297 std::array<unsigned char, o2::itsmft::ClusterPattern::MaxPatternBytes> patt{};
298 for (
const auto& [
r,
c] : tileCells) {
299 uint32_t
ir =
r - tileRowMin;
300 uint32_t ic =
c - tileColMin;
301 int nbit =
ir * tileColSpan + ic;
302 patt[nbit >> 3] |= (0x1 << (7 - (nbit % 8)));
304 patterns.emplace_back(
static_cast<unsigned char>(tileRowSpan));
305 patterns.emplace_back(
static_cast<unsigned char>(tileColSpan));
306 const int nBytes = (tileRowSpan * tileColSpan + 7) / 8;
307 patterns.insert(patterns.end(), patt.begin(), patt.begin() + nBytes);
310 if (clusterLabels && digitLabels) {
311 const auto clsIdx =
static_cast<uint32_t
>(
clusters.size());
312 for (
const auto& cell : actsCluster.cells) {
313 uint16_t
r =
static_cast<uint16_t
>(cell.row);
314 uint16_t
c =
static_cast<uint16_t
>(cell.col);
315 if (
r >= tileRowMin && r <= tileRowMax && c >= tileColMin &&
c <= tileColMax) {
317 const auto& lbls = digitLabels->
getLabels(cell.digitIdx);
318 for (
const auto& lbl : lbls) {
329 cluster.
row = tileRowMin;
330 cluster.
col = tileColMin;
331 cluster.
size =
static_cast<uint16_t
>(tileCells.size());
333 cluster.
subDetID =
static_cast<int16_t
>(geom->getSubDetID(chipID));
334 cluster.
layer =
static_cast<int16_t
>(geom->getLayer(chipID));
341 std::array<unsigned char, o2::itsmft::ClusterPattern::MaxPatternBytes> patt{};
342 for (
const auto& cell : actsCluster.cells) {
343 uint32_t
ir =
static_cast<uint32_t
>(cell.row - rowMin);
344 uint32_t ic =
static_cast<uint32_t
>(cell.col - colMin);
345 int nbit =
ir * colSpan + ic;
346 patt[nbit >> 3] |= (0x1 << (7 - (nbit % 8)));
348 patterns.emplace_back(
static_cast<unsigned char>(rowSpan));
349 patterns.emplace_back(
static_cast<unsigned char>(colSpan));
350 const int nBytes = (rowSpan * colSpan + 7) / 8;
351 patterns.insert(patterns.end(), patt.begin(), patt.begin() + nBytes);
354 if (clusterLabels && digitLabels) {
355 const auto clsIdx =
static_cast<uint32_t
>(
clusters.size());
356 for (
const auto& cell : actsCluster.cells) {
358 const auto& lbls = digitLabels->
getLabels(cell.digitIdx);
359 for (
const auto& lbl : lbls) {
369 cluster.
row = rowMin;
370 cluster.
col = colMin;
371 cluster.
size =
static_cast<uint16_t
>(actsCluster.cells.size());
373 cluster.
subDetID =
static_cast<int16_t
>(geom->getSubDetID(chipID));
374 cluster.
layer =
static_cast<int16_t
>(geom->getLayer(chipID));
380 LOG(
debug) <<
" clusterization of chip " << chipID <<
" completed!";
382 clusterROFs.emplace_back(inROF.getBCData(), inROF.getROFrame(),
383 outFirst,
static_cast<int>(
clusters.size()) - outFirst);