[base] Remove base::fold and base::all
They can be replaced by std::conjunction and c++17 folding expressions. R=tebbi@chromium.org Bug: v8:12425 Change-Id: I109ac904245aab431f11752eff5129fd4361de8a Reviewed-on: https://chromium-review.googlesource.com/c/v8/v8/+/3570428 Reviewed-by: Tobias Tebbi <tebbi@chromium.org> Commit-Queue: Clemens Backes <clemensb@chromium.org> Cr-Commit-Position: refs/heads/main@{#79843}
This commit is contained in:
parent
16b5fc3c57
commit
9f128f4e9f
@ -60,19 +60,6 @@ struct has_output_operator<
|
||||
T, TStream, decltype(void(std::declval<TStream&>() << std::declval<T>()))>
|
||||
: std::true_type {};
|
||||
|
||||
// Fold all arguments from left to right with a given function.
|
||||
template <typename Func, typename T>
|
||||
constexpr auto fold(Func func, T&& t) {
|
||||
return std::forward<T>(t);
|
||||
}
|
||||
|
||||
template <typename Func, typename T1, typename T2, typename... Ts>
|
||||
constexpr auto fold(Func func, T1&& first, T2&& second, Ts&&... more) {
|
||||
auto&& folded = func(std::forward<T1>(first), std::forward<T2>(second));
|
||||
return fold(std::move(func), std::forward<decltype(folded)>(folded),
|
||||
std::forward<Ts>(more)...);
|
||||
}
|
||||
|
||||
// {is_same<Ts...>::value} is true if all Ts are the same, false otherwise.
|
||||
template <typename... Ts>
|
||||
struct is_same : public std::false_type {};
|
||||
@ -83,12 +70,6 @@ struct is_same<T> : public std::true_type {};
|
||||
template <typename T, typename... Ts>
|
||||
struct is_same<T, T, Ts...> : public is_same<T, Ts...> {};
|
||||
|
||||
// Returns true, iff all values (implicitly converted to bool) are trueish.
|
||||
template <typename... Args>
|
||||
constexpr bool all(Args... rest) {
|
||||
return fold(std::logical_and<>{}, true, rest...);
|
||||
}
|
||||
|
||||
} // namespace base
|
||||
} // namespace v8
|
||||
|
||||
|
@ -26,12 +26,8 @@ class V8_EXPORT_PRIVATE CPURegList {
|
||||
public:
|
||||
template <typename... CPURegisters>
|
||||
explicit CPURegList(CPURegister reg0, CPURegisters... regs)
|
||||
: list_(base::fold(
|
||||
[](uint64_t acc, CPURegister v) {
|
||||
if (!v.is_valid()) return acc;
|
||||
return acc | (uint64_t{1} << v.code());
|
||||
},
|
||||
0, reg0, regs...)),
|
||||
: list_(((uint64_t{1} << reg0.code()) | ... |
|
||||
(regs.is_valid() ? uint64_t{1} << regs.code() : 0))),
|
||||
size_(reg0.SizeInBits()),
|
||||
type_(reg0.type()) {
|
||||
DCHECK(AreSameSizeAndType(reg0, regs...));
|
||||
|
@ -20,22 +20,14 @@ constexpr bool ShouldPadArguments(int argument_count) {
|
||||
}
|
||||
|
||||
#ifdef DEBUG
|
||||
struct CountIfValidRegisterFunctor {
|
||||
template <typename RegType>
|
||||
constexpr int operator()(int count, RegType reg) const {
|
||||
return count + (reg.is_valid() ? 1 : 0);
|
||||
}
|
||||
};
|
||||
|
||||
template <typename RegType, typename... RegTypes,
|
||||
template <typename... RegTypes,
|
||||
// All arguments must be either Register or DoubleRegister.
|
||||
typename = typename std::enable_if<
|
||||
base::is_same<Register, RegType, RegTypes...>::value ||
|
||||
base::is_same<DoubleRegister, RegType, RegTypes...>::value>::type>
|
||||
inline constexpr bool AreAliased(RegType first_reg, RegTypes... regs) {
|
||||
int num_different_regs = RegListBase<RegType>{first_reg, regs...}.Count();
|
||||
int num_given_regs =
|
||||
base::fold(CountIfValidRegisterFunctor{}, 0, first_reg, regs...);
|
||||
base::is_same<Register, RegTypes...>::value ||
|
||||
base::is_same<DoubleRegister, RegTypes...>::value>::type>
|
||||
inline constexpr bool AreAliased(RegTypes... regs) {
|
||||
int num_different_regs = RegListBase{regs...}.Count();
|
||||
int num_given_regs = (... + (regs.is_valid() ? 1 : 0));
|
||||
return num_different_regs < num_given_regs;
|
||||
}
|
||||
#endif
|
||||
|
@ -70,7 +70,7 @@ class V8_EXPORT_PRIVATE Graph final : public NON_EXPORTED_BASE(ZoneObject) {
|
||||
// for argument types convertible to Node* during overload resolution.
|
||||
template <typename... Nodes,
|
||||
typename = typename std::enable_if_t<
|
||||
base::all(std::is_convertible<Nodes, Node*>::value...)>>
|
||||
std::conjunction_v<std::is_convertible<Nodes, Node*>...>>>
|
||||
Node* NewNode(const Operator* op, Nodes... nodes) {
|
||||
std::array<Node*, sizeof...(nodes)> nodes_arr{
|
||||
{static_cast<Node*>(nodes)...}};
|
||||
|
@ -107,63 +107,6 @@ static_assert(has_output_operator<TestClass3>::value,
|
||||
static_assert(has_output_operator<const TestClass3>::value,
|
||||
"const TestClass3 can be output");
|
||||
|
||||
//////////////////////////////
|
||||
// Test fold.
|
||||
//////////////////////////////
|
||||
|
||||
struct FoldAllSameType {
|
||||
constexpr uint32_t operator()(uint32_t a, uint32_t b) const { return a | b; }
|
||||
};
|
||||
static_assert(base::fold(FoldAllSameType{}, 3, 6) == 7, "check fold");
|
||||
// Test that it works if implicit conversion is needed for one of the
|
||||
// parameters.
|
||||
static_assert(base::fold(FoldAllSameType{}, uint8_t{1}, 256) == 257,
|
||||
"check correct type inference");
|
||||
// Test a single parameter.
|
||||
static_assert(base::fold(FoldAllSameType{}, 25) == 25,
|
||||
"check folding a single argument");
|
||||
|
||||
TEST(TemplateUtilsTest, FoldDifferentType) {
|
||||
auto fn = [](std::string str, char c) {
|
||||
str.push_back(c);
|
||||
return str;
|
||||
};
|
||||
CHECK_EQ(base::fold(fn, std::string("foo"), 'b', 'a', 'r'), "foobar");
|
||||
}
|
||||
|
||||
TEST(TemplateUtilsTest, FoldMoveOnlyType) {
|
||||
auto fn = [](std::unique_ptr<std::string> str, char c) {
|
||||
str->push_back(c);
|
||||
return str;
|
||||
};
|
||||
std::unique_ptr<std::string> str = std::make_unique<std::string>("foo");
|
||||
std::unique_ptr<std::string> folded =
|
||||
base::fold(fn, std::move(str), 'b', 'a', 'r');
|
||||
CHECK_NULL(str);
|
||||
CHECK_NOT_NULL(folded);
|
||||
CHECK_EQ(*folded, "foobar");
|
||||
}
|
||||
|
||||
struct TemplatizedFoldFunctor {
|
||||
template <typename T, typename... Tup>
|
||||
std::tuple<Tup..., typename std::decay<T>::type> operator()(
|
||||
std::tuple<Tup...> tup, T&& val) {
|
||||
return std::tuple_cat(std::move(tup),
|
||||
std::make_tuple(std::forward<T>(val)));
|
||||
}
|
||||
};
|
||||
TEST(TemplateUtilsTest, FoldToTuple) {
|
||||
auto input = std::make_tuple(char{'x'}, int{4}, double{3.2},
|
||||
std::unique_ptr<uint8_t>{}, std::string{"foo"});
|
||||
auto result =
|
||||
base::fold(TemplatizedFoldFunctor{}, std::make_tuple(),
|
||||
std::get<0>(input), std::get<1>(input), std::get<2>(input),
|
||||
std::unique_ptr<uint8_t>{}, std::get<4>(input));
|
||||
static_assert(std::is_same<decltype(result), decltype(input)>::value,
|
||||
"the resulting tuple should have the same type as the input");
|
||||
DCHECK_EQ(input, result);
|
||||
}
|
||||
|
||||
} // namespace template_utils_unittest
|
||||
} // namespace base
|
||||
} // namespace v8
|
||||
|
Loading…
Reference in New Issue
Block a user