I have some predicate objects that take some value and return the result of some criteria. (My real implementation is more complex, this is only a minimal example):
struct PredEven
{
bool passes(int x) const { return x%2 == 0; }
};
struct PredGreaterThan
{
int limit;
bool passes(int x) const { return x > limit; }
};
using Predicate = std::variant<PredEven, PredGreaterThan>;
I store objects of these types in a std::array and now want to test some value against all of these.
The straight-forward implementation would be this:
const std::array<Predicate, 2> predicates = {PredEven{}, PredGreaterThan{3}};
const int valToTest = 4;
bool allPassed1 = true;
for(const auto& var : predicates)
{
allPassed1 &= std::visit([&valToTest](const auto& p){ return p.passes(valToTest); }, var);
}
However, I really should be using std::all_of for this. Better yet, the ranges version:
const bool allPassed2 = std::ranges::all_of(predicates, [&valToTest](const auto& var)
{ return std::visit([&valToTest](const auto& p){ return p.passes(valToTest); }, var); });
This code is concise but rather hard to read (and to format). Particularly the nested lambda isn't great. It does have the advantage that the result can be const.
Is there any way to get rid of the nested lambda or make this more readable?