diff --git a/atcoder/lazysegtree.hpp b/atcoder/lazysegtree.hpp index 2119d82..c858663 100644 --- a/atcoder/lazysegtree.hpp +++ b/atcoder/lazysegtree.hpp @@ -3,13 +3,38 @@ #include #include -#include +#include #include #include "atcoder/internal_bit" namespace atcoder { +#if __cplusplus >= 201703L + +template +struct lazy_segtree { + static_assert(std::is_convertible_v>, + "op must work as S(S, S)"); + static_assert(std::is_convertible_v>, + "e must work as S()"); + static_assert( + std::is_convertible_v>, + "mapping must work as F(F, S)"); + static_assert( + std::is_convertible_v>, + "compostiion must work as F(F, F)"); + static_assert(std::is_convertible_v>, + "id must work as F()"); + +#else + template struct lazy_segtree { + +#endif + public: lazy_segtree() : lazy_segtree(0) {} explicit lazy_segtree(int n) : lazy_segtree(std::vector(n, e())) {} diff --git a/atcoder/segtree.hpp b/atcoder/segtree.hpp index c8bfef6..c8b0e59 100644 --- a/atcoder/segtree.hpp +++ b/atcoder/segtree.hpp @@ -3,13 +3,27 @@ #include #include +#include #include #include "atcoder/internal_bit" namespace atcoder { +#if __cplusplus >= 201703L + +template struct segtree { + static_assert(std::is_convertible_v>, + "op must work as S(S, S)"); + static_assert(std::is_convertible_v>, + "e must work as S()"); + +#else + template struct segtree { + +#endif + public: segtree() : segtree(0) {} explicit segtree(int n) : segtree(std::vector(n, e())) {} diff --git a/test/unittest/lazysegtree_test.cpp b/test/unittest/lazysegtree_test.cpp index d408a6b..bcd9bd2 100644 --- a/test/unittest/lazysegtree_test.cpp +++ b/test/unittest/lazysegtree_test.cpp @@ -85,3 +85,33 @@ TEST(LazySegtreeTest, Usage) { ASSERT_EQ(-5, seg.prod(2, 3)); ASSERT_EQ(0, seg.prod(2, 4)); } + +#if __cplusplus >= 201703L + +int op_const(const int& a, const int& b) { return std::max(a, b); } + +struct const_starry { + static int op_ss(const int& a, const int& b) { return std::max(a, b); } + static int op_ts(const int& a, const int& b) { return a + b; } + static int op_tt(const int& a, const int& b) { return a + b; } +}; + +TEST(SegtreeTest, ConstFunc) { + lazy_segtree + seg(10); +} + +#endif + +#if __cplusplus >= 202002L + +TEST(LazySegtreeTest, LambdaFunc) { + lazy_segtree + seg(10); +} + +#endif diff --git a/test/unittest/segtree_test.cpp b/test/unittest/segtree_test.cpp index 0f49e1c..0a533e6 100644 --- a/test/unittest/segtree_test.cpp +++ b/test/unittest/segtree_test.cpp @@ -144,3 +144,28 @@ TEST(SegtreeTest, Assign) { seg seg0; seg0 = seg(10); } + +#if __cplusplus >= 201703L + +std::string op_const(const std::string& a, const std::string& b) { + assert(a == "$" || b == "$" || a <= b); + if (a == "$") return b; + if (b == "$") return a; + return a + b; +} + +TEST(SegtreeTest, ConstFunc) { + segtree s1(10); +} + +#endif + +#if __cplusplus >= 202002L + +TEST(SegtreeTest, LambdaFunc) { + segtree s1(10); +} + +#endif