Skip to content

Commit

Permalink
c++17 concepts with CPP_template for engine/*.{cpp,h} files
Browse files Browse the repository at this point in the history
  • Loading branch information
Sebastian Wieczorek authored and Sebastian Wieczorek committed Feb 17, 2025
1 parent a9f6895 commit c33b909
Show file tree
Hide file tree
Showing 4 changed files with 63 additions and 56 deletions.
36 changes: 19 additions & 17 deletions src/engine/GroupBy.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -432,10 +432,11 @@ ProtoResult GroupBy::computeResult(bool requestLaziness) {
}

// _____________________________________________________________________________
template <int COLS>
size_t GroupBy::searchBlockBoundaries(
const std::invocable<size_t, size_t> auto& onBlockChange,
const IdTableView<COLS>& idTable, GroupBlock& currentGroupBlock) const {
CPP_template_def(int COLS,
typename T)(requires ranges::invocable<T, size_t, size_t>)
size_t GroupBy::searchBlockBoundaries(const T& onBlockChange,
const IdTableView<COLS>& idTable,
GroupBlock& currentGroupBlock) const {
size_t blockStart = 0;

for (size_t pos = 0; pos < idTable.size(); pos++) {
Expand Down Expand Up @@ -1252,18 +1253,19 @@ GroupBy::HashMapAggregationData<NUM_GROUP_COLUMNS>::getHashEntries(
hashEntries.push_back(iterator->second);
}

auto resizeVectors =
[]<VectorOfAggregationData T>(
T& arg, size_t numberOfGroups,
[[maybe_unused]] const HashMapAggregateTypeWithData& info) {
if constexpr (std::same_as<typename T::value_type,
GroupConcatAggregationData>) {
arg.resize(numberOfGroups,
GroupConcatAggregationData{info.separator_.value()});
} else {
arg.resize(numberOfGroups);
}
};
// CPP_template_lambda(capture)(typenames...)(arg)(requires ...)`
auto resizeVectors = CPP_template_lambda()(typename T)(
T & arg, size_t numberOfGroups,
[[maybe_unused]] const HashMapAggregateTypeWithData& info)(
requires true) {
if constexpr (std::same_as<typename T::value_type,
GroupConcatAggregationData>) {
arg.resize(numberOfGroups,
GroupConcatAggregationData{info.separator_.value()});
} else {
arg.resize(numberOfGroups);
}
};

// TODO<C++23> use views::enumerate
auto idx = 0;
Expand All @@ -1273,7 +1275,7 @@ GroupBy::HashMapAggregationData<NUM_GROUP_COLUMNS>::getHashEntries(

std::visit(
[&resizeVectors, &aggregationTypeWithData,
numberOfGroups]<VectorOfAggregationData T>(T& arg) {
numberOfGroups]<typename T>(T& arg) {
resizeVectors(arg, numberOfGroups, aggregationTypeWithData);
},
aggregation);
Expand Down
10 changes: 6 additions & 4 deletions src/engine/GroupBy.h
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@
#include <utility>
#include <vector>

#include "backports/concepts.h"
#include "engine/GroupByHashMapOptimization.h"
#include "engine/Join.h"
#include "engine/Operation.h"
Expand Down Expand Up @@ -112,10 +113,11 @@ class GroupBy : public Operation {
// function returns the starting index of the last block of this `idTable`.
// The argument `currentGroupBlock` is used to store the values of the group
// by columns for the current group.
template <int COLS>
size_t searchBlockBoundaries(
const std::invocable<size_t, size_t> auto& onBlockChange,
const IdTableView<COLS>& idTable, GroupBlock& currentGroupBlock) const;
CPP_template(int COLS,
typename T)(requires ranges::invocable<T, size_t, size_t>) size_t
searchBlockBoundaries(const T& onBlockChange,
const IdTableView<COLS>& idTable,
GroupBlock& currentGroupBlock) const;

// Helper function to process a sorted group within a single id table.
template <size_t OUT_WIDTH>
Expand Down
6 changes: 3 additions & 3 deletions src/engine/GroupByHashMapOptimization.h
Original file line number Diff line number Diff line change
Expand Up @@ -13,9 +13,9 @@
// For `AVG`, add value to sum if it is numeric, otherwise
// set error flag.
static constexpr auto valueAdder = []() {
auto numericValueAdder =
[]<typename T>(T value, double& sum, [[maybe_unused]] const bool& error)
requires std::is_arithmetic_v<T> {
auto numericValueAdder = []<typename T>(T value, double& sum,
[[maybe_unused]] const bool& error)
-> CPP_ret(void)(requires std::is_arithmetic_v<T>) {
sum += static_cast<double>(value);
};
auto nonNumericValueAdder = [](sparqlExpression::detail::NotNumeric,
Expand Down
67 changes: 35 additions & 32 deletions src/engine/QueryPlanner.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -526,7 +526,7 @@ namespace {
// `TripleComponent`, typically the subject, predicate, or object of the triple,
// hence the name.
template <typename Function>
concept TriplePosition =
CPP_concept TriplePosition =
ad_utility::InvocableWithExactReturnType<Function, TripleComponent&,
SparqlTripleSimple&>;

Expand All @@ -544,31 +544,32 @@ SparqlFilter createEqualFilter(const Variable& var1, const Variable& var2) {
// position of the `scanTriple`, denoted by the `rewritePosition` by a new
// variable, and add a filter, that checks the old and the new value for
// equality.
constexpr auto rewriteSingle =
[](TriplePosition auto rewritePosition, SparqlTripleSimple& scanTriple,
const auto& addFilter, const auto& generateUniqueVarName) {
Variable filterVar = generateUniqueVarName();
auto& target = std::invoke(rewritePosition, scanTriple).getVariable();
addFilter(createEqualFilter(filterVar, target));
target = filterVar;
};
constexpr auto rewriteSingle = CPP_template_lambda()(typename T)(
T rewritePosition, SparqlTripleSimple& scanTriple, const auto& addFilter,
const auto& generateUniqueVarName)(requires TriplePosition<T>) {
Variable filterVar = generateUniqueVarName();
auto& target = std::invoke(rewritePosition, scanTriple).getVariable();
addFilter(createEqualFilter(filterVar, target));
target = filterVar;
};

// Replace the positions of the `triple` that are specified by the
// `rewritePositions` with a new variable, and add a filter, which checks the
// old and the new value for equality for each of these rewrites. Then also
// add an index scan for the rewritten triple.
constexpr auto handleRepeatedVariablesImpl =
[](const auto& triple, auto& addIndexScan,
const auto& generateUniqueVarName, const auto& addFilter,
std::span<const Permutation::Enum> permutations,
TriplePosition auto... rewritePositions) {
auto scanTriple = triple;
(..., rewriteSingle(rewritePositions, scanTriple, addFilter,
generateUniqueVarName));
for (const auto& permutation : permutations) {
addIndexScan(permutation, scanTriple);
}
};
[]<typename... T>(const auto& triple, auto& addIndexScan,
const auto& generateUniqueVarName, const auto& addFilter,
std::span<const Permutation::Enum> permutations,
T... rewritePositions)
-> CPP_ret(void)(requires(TriplePosition<T>&&...)) {
auto scanTriple = triple;
(..., rewriteSingle(rewritePositions, scanTriple, addFilter,
generateUniqueVarName));
for (const auto& permutation : permutations) {
addIndexScan(permutation, scanTriple);
}
};

} // namespace

Expand Down Expand Up @@ -601,13 +602,14 @@ void QueryPlanner::indexScanTwoVarsCase(
// add an index scan for the rewritten triple.
auto generate = [this]() { return generateUniqueVarName(); };
auto handleRepeatedVariables =
[&triple, &addIndexScan, &addFilter, &generate](
[&triple, &addIndexScan, &addFilter, &generate]<typename... T>(
std::span<const Permutation::Enum> permutations,
TriplePosition auto... rewritePositions) {
return handleRepeatedVariablesImpl(triple, addIndexScan, generate,
addFilter, permutations,
rewritePositions...);
};
T... rewritePositions)
-> CPP_ret(void)(requires(TriplePosition<T>&&...)) {
return handleRepeatedVariablesImpl(triple, addIndexScan, generate,
addFilter, permutations,
rewritePositions...);
};

const auto& [s, p, o, _] = triple;

Expand Down Expand Up @@ -653,13 +655,14 @@ void QueryPlanner::indexScanThreeVarsCase(
// old and the new value for equality for this rewrite. Then also
// add an index scan for the rewritten triple.
auto handleRepeatedVariables =
[&triple, &addIndexScan, &addFilter, &generate](
[&triple, &addIndexScan, &addFilter, &generate]<typename... T>(
std::span<const Permutation::Enum> permutations,
TriplePosition auto... rewritePositions) {
return handleRepeatedVariablesImpl(triple, addIndexScan, generate,
addFilter, permutations,
rewritePositions...);
};
T... rewritePositions)
-> CPP_ret(void)(requires(TriplePosition<T>&&...)) {
return handleRepeatedVariablesImpl(triple, addIndexScan, generate,
addFilter, permutations,
rewritePositions...);
};

using Tr = SparqlTripleSimple;
const auto& [s, p, o, _] = triple;
Expand Down

0 comments on commit c33b909

Please sign in to comment.