結果
問題 | No.3145 Astral Parentheses Sequence |
ユーザー |
👑 ![]() |
提出日時 | 2025-05-16 22:24:14 |
言語 | C++17 (gcc 13.3.0 + boost 1.87.0) |
結果 |
AC
|
実行時間 | 93 ms / 2,000 ms |
コード長 | 4,583 bytes |
コンパイル時間 | 596 ms |
コンパイル使用メモリ | 78,880 KB |
実行使用メモリ | 6,272 KB |
最終ジャッジ日時 | 2025-05-16 22:24:18 |
合計ジャッジ時間 | 3,219 ms |
ジャッジサーバーID (参考情報) |
judge4 / judge1 |
(要ログイン)
ファイルパターン | 結果 |
---|---|
sample | AC * 3 |
other | AC * 45 |
ソースコード
#ifdef NACHIA #define _GLIBCXX_DEBUG #else #define NDEBUG #endif #include <iostream> #include <string> #include <vector> #include <algorithm> using i64 = long long; using u64 = unsigned long long; #define rep(i,n) for(i64 i=0; i<i64(n); i++) const i64 INF = 1001001001001001001; template<typename A> void chmin(A& l, const A& r){ if(r < l) l = r; } template<typename A> void chmax(A& l, const A& r){ if(l < r) l = r; } using namespace std; #include <cassert> #include <utility> namespace nachia{ // ax + by = gcd(a,b) // return ( x, - ) std::pair<long long, long long> ExtGcd(long long a, long long b){ long long x = 1, y = 0; while(b){ long long u = a / b; std::swap(a-=b*u, b); std::swap(x-=y*u, y); } return std::make_pair(x, a); } } // namespace nachia namespace nachia{ class DynamicModSupplier{ using u64 = unsigned long long; using Int = unsigned int; private: u64 imod; Int mod; // atcoder library u64 reduce2(u64 z) const noexcept { // atcoder library #ifdef _MSC_VER u64 x; _umul128(z, im, &x); #else using u128 = unsigned __int128; u64 x = (u64)(((u128)(z)*imod) >> 64); #endif return z - x * mod; } public: DynamicModSupplier(unsigned int MOD = 998244353) : mod(MOD) { assert(2 <= MOD); assert(MOD < (1u << 31)); imod = (u64)(-1) / mod + 1; } Int reduce(u64 z) const noexcept { Int v = reduce2(z); if(mod <= v) v += mod; return v; } Int add(Int a, Int b) const { a += b; if(a >= mod){ a -= mod; } return a; } Int sub(Int a, Int b) const { a -= b; if(a >= mod){ a += mod; } return a; } Int mul(Int a, Int b) const { return reduce((u64)a * b); } Int muladd(Int a, Int b, Int c) const { return reduce((u64)a * b + c); } Int inv(Int a) const { Int v = ExtGcd(a, mod).first; return (v < mod) ? v : (v + mod); } Int pow(Int a, u64 i) const { Int r = a, ans = 1; while(i){ if(i & 1) ans = mul(ans, r); i /= 2; r = mul(r, r); } return ans; } Int getMod() const { return mod; } }; } // namespace nachia namespace nachia{ template<unsigned int IDENTIFER, class IDENTIFER2 = void> class DynamicModint{ using Int = unsigned int; using MyType = DynamicModint; private: static DynamicModSupplier _c; Int v; template< class Elem > static Elem SafeMod(Elem x, Int mod){ if(x < 0){ if(0 <= x+mod) return x + mod; return mod - ((-(x+mod)-1) % mod + 1); } return x % mod; } public: DynamicModint() : v(0) {} DynamicModint(const MyType& r) : v(r.v) {} MyType& operator=(const MyType&) = default; DynamicModint(long long x){ v = SafeMod(x, _c.getMod()); } static MyType raw(Int _v){ MyType res; res.v = _v; return res; } static void setMod(DynamicModSupplier sup){ _c = std::move(sup); } MyType operator+=(MyType r){ return v = _c.add(v, r.v); } MyType operator+(MyType r) const { return raw(_c.add(v, r.v)); } MyType operator-=(MyType r){ return v = _c.sub(v, r.v); } MyType operator-(MyType r) const { return raw(_c.sub(v, r.v)); } MyType operator-() const { return raw(v ? _c.getMod()-v : 0); } MyType operator*=(MyType r){ return v = _c.mul(v, r.v); } MyType operator*(MyType r) const { return raw(_c.mul(v, r.v)); } MyType operator/=(MyType r){ return v = _c.mul(v, _c.inv(r.v)); } MyType operator/(MyType r) const { return raw(_c.mul(v, _c.inv(r.v))); } MyType inv() const { return raw(_c.inv(v)); } MyType pow(unsigned long long r) const { return raw(_c.pow(v, r)); } MyType mulAdd(MyType mul, MyType add) const { return raw(_c.muladd(v, mul.v, add.v)); } Int val() const { return v; } Int operator*() const { return v; } static Int mod(){ return _c.getMod(); } }; template<unsigned int IDENTIFER, class IDENTIFER2> DynamicModSupplier DynamicModint<IDENTIFER, IDENTIFER2>::_c; } // namespace nachia using Modint = nachia::DynamicModint<2>; void testcase(){ i64 N, M; cin >> N >> M; if(N%3 != 0){ cout << "0\n"; return; } N /= 3; Modint::setMod(M); vector<Modint> dp(N+1); dp[0] = 1; for(i64 i=1; i<=N; i++){ for(i64 a=0; a<i; a++){ for(i64 b=0; a+b<i; b++){ dp[i] += dp[a] * dp[b] * dp[i-1-a-b]; } } } cout << dp[N].val() << "\n"; } int main(){ ios::sync_with_stdio(false); cin.tie(nullptr); testcase(); return 0; }