Analysis Software
Documentation for sPHENIX simulation software
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
WhiteBoard.cpp
Go to the documentation of this file. Or view the newest version in sPHENIX GitHub for file WhiteBoard.cpp
1 // This file is part of the Acts project.
2 //
3 // Copyright (C) 2022 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 
11 #include <array>
12 #include <string_view>
13 
14 #include <Eigen/Core>
15 #include <boost/core/demangle.hpp>
16 
17 namespace {
18 
20 inline int levenshteinDistance(const std::string_view &a,
21  const std::string_view &b) {
22  // for all i and j, d[i,j] will hold the Levenshtein distance between
23  // the first i characters of s and the first j characters of t
24  Eigen::MatrixXi d = Eigen::MatrixXi::Zero(a.size() + 1, b.size() + 1);
25 
26  // source prefixes can be transformed into empty string by
27  // dropping all characters
28  for (std::size_t i = 1; i < a.size() + 1; ++i) {
29  d(i, 0) = i;
30  }
31 
32  // target prefixes can be reached from empty source prefix
33  // by inserting every character
34  for (std::size_t j = 1; j < b.size() + 1; ++j) {
35  d(0, j) = j;
36  }
37 
38  // Fill matrix
39  for (std::size_t j = 1; j < b.size() + 1; ++j) {
40  for (std::size_t i = 1; i < a.size() + 1; ++i) {
41  const auto substitutionCost = a[i] == b[j] ? 0 : 1;
42 
43  std::array<int, 3> possibilities = {{
44  d(i - 1, j) + 1, // deletion
45  d(i, j - 1) + 1, // insertion
46  d(i - 1, j - 1) + substitutionCost // substitution
47  }};
48 
49  d(i, j) = *std::min_element(possibilities.begin(), possibilities.end());
50  }
51  }
52 
53  // std::cout << "\n" << d << "\n";
54 
55  return d(a.size(), b.size());
56 }
57 
58 } // namespace
59 
60 std::vector<std::string_view> ActsExamples::WhiteBoard::similarNames(
61  const std::string_view &name, int distThreshold,
62  std::size_t maxNumber) const {
63  std::vector<std::pair<int, std::string_view>> names;
64  for (const auto &[n, h] : m_store) {
65  if (const auto d = levenshteinDistance(n, name); d < distThreshold) {
66  names.push_back({d, n});
67  }
68  }
69 
70  std::sort(names.begin(), names.end(),
71  [&](const auto &a, const auto &b) { return a.first < b.first; });
72 
73  std::vector<std::string_view> selected_names;
74  for (std::size_t i = 0; i < std::min(names.size(), maxNumber); ++i) {
75  selected_names.push_back(names[i].second);
76  }
77 
78  return selected_names;
79 }
80 
82  const std::string &name, const char *req, const char *act) {
83  return std::string{"Type mismatch for '" + name + "'. Requested " +
84  boost::core::demangle(req) + " but actually " +
85  boost::core::demangle(act)};
86 }