@@ -139,6 +139,7 @@ struct TupleTests {
139139 test (17 == TupFn{}.apply ([]() { return 17 ; }, empty));
140140
141141 Tup t{1 , 2 , 3 };
142+ TupFn{}.apply ([t](auto ... n) { test (t == Tup{n...}); }, t);
142143 test (6 == TupFn{}.apply ([](auto ... n) { return (n + ...); }, t));
143144 TupFn{}.apply ([](auto &... n) { return ((n *= n), ...); }, t);
144145 test (Tup{1 , 4 , 9 } == t);
@@ -147,11 +148,11 @@ struct TupleTests {
147148 }
148149
149150 static constexpr bool check_apply_move () {
150- Tup moveT{MoveOnly{}, MoveOnly{}};
151+ Tup moveT{MoveOnly{}, std::optional< MoveOnly> {}};
151152 auto m = TupFn{}.apply (
152153 [](auto && m1, auto m2) {
153154 static_assert (std::is_same_v<decltype (m1), MoveOnly&&>);
154- static_assert (std::is_same_v<decltype (m2), MoveOnly>);
155+ static_assert (std::is_same_v<decltype (m2), std::optional< MoveOnly> >);
155156 return std::move (m1);
156157 },
157158 std::move (moveT));
@@ -335,6 +336,56 @@ TEST(LiteTupleTest, lite_tuple_cat_move_unique_ptr) {
335336 LiteTests::check_tuple_cat_move_unique_ptr ();
336337}
337338
339+ constexpr bool check_lite_tuple_reverse_apply () { // no `std::reverse_apply`
340+ lite_tuple::tuple empty{};
341+ test (17 == lite_tuple::reverse_apply ([]() { return 17 ; }, empty));
342+
343+ lite_tuple::tuple t{1 , 2 , 3 };
344+ lite_tuple::reverse_apply (
345+ [](auto ... n) {
346+ test (lite_tuple::tuple{3 , 2 , 1 } == lite_tuple::tuple{n...});
347+ },
348+ t);
349+ lite_tuple::reverse_apply ([](auto &... n) { return ((n *= n), ...); }, t);
350+ test (lite_tuple::tuple{1 , 4 , 9 } == t);
351+
352+ lite_tuple::tuple moveT{MoveOnly{}, std::optional<MoveOnly>{}};
353+ auto m = lite_tuple::reverse_apply (
354+ [](auto && m1, auto m2) {
355+ static_assert (std::is_same_v<decltype (m1), std::optional<MoveOnly>&&>);
356+ static_assert (std::is_same_v<decltype (m2), MoveOnly>);
357+ return std::move (m1);
358+ },
359+ std::move (moveT));
360+ static_assert (std::is_same_v<decltype (m), std::optional<MoveOnly>>);
361+
362+ int n = 5 ;
363+ lite_tuple::reverse_apply (
364+ [](auto && lref, auto && rref) {
365+ static_assert (std::is_same_v<int &&, decltype (rref)>);
366+ static_assert (std::is_same_v<int &, decltype (lref)>);
367+ },
368+ // NOLINTNEXTLINE(performance-move-const-arg)
369+ // @lint-ignore CLANGTIDY facebook-hte-MoveEvaluationOrder
370+ lite_tuple::forward_as_tuple (std::move (n), n));
371+
372+ return true ;
373+ }
374+
375+ static_assert (check_lite_tuple_reverse_apply());
376+
377+ TEST (LiteTupleTest, lite_tuple_reverse_apply) { // no `std::reverse_apply`
378+ lite_tuple::tuple moveT{std::make_unique<int >(7 ), MoveOnly{}};
379+ auto p = lite_tuple::reverse_apply (
380+ [](auto m, auto && p) {
381+ static_assert (std::is_same_v<decltype (m), MoveOnly>);
382+ return std::move (p);
383+ },
384+ std::move (moveT));
385+ EXPECT_EQ (7 , *p);
386+ EXPECT_EQ (nullptr , lite_tuple::get<0 >(moveT).get ());
387+ }
388+
338389} // namespace folly::detail
339390
340391FOLLY_POP_WARNING
0 commit comments