結果

問題 No.2303 Frog on Grid
ユーザー navel_tosnavel_tos
提出日時 2023-06-01 13:15:21
言語 PyPy3
(7.3.15)
結果
AC  
実行時間 1,230 ms / 2,000 ms
コード長 3,073 bytes
コンパイル時間 833 ms
コンパイル使用メモリ 87,052 KB
実行使用メモリ 105,140 KB
最終ジャッジ日時 2023-08-28 02:03:12
合計ジャッジ時間 18,449 ms
ジャッジサーバーID
(参考情報)
judge13 / judge14
このコードへのチャレンジ
(要ログイン)

テストケース

テストケース表示
入力 結果 実行時間
実行使用メモリ
testcase_00 AC 109 ms
83,608 KB
testcase_01 AC 119 ms
84,204 KB
testcase_02 AC 1,215 ms
101,324 KB
testcase_03 AC 639 ms
92,844 KB
testcase_04 AC 1,218 ms
101,504 KB
testcase_05 AC 1,221 ms
101,772 KB
testcase_06 AC 635 ms
93,032 KB
testcase_07 AC 1,217 ms
100,788 KB
testcase_08 AC 1,230 ms
101,080 KB
testcase_09 AC 362 ms
88,692 KB
testcase_10 AC 646 ms
92,772 KB
testcase_11 AC 355 ms
89,112 KB
testcase_12 AC 640 ms
93,340 KB
testcase_13 AC 107 ms
83,752 KB
testcase_14 AC 107 ms
83,756 KB
testcase_15 AC 108 ms
83,580 KB
testcase_16 AC 106 ms
83,792 KB
testcase_17 AC 106 ms
83,516 KB
testcase_18 AC 1,216 ms
104,944 KB
testcase_19 AC 1,216 ms
104,920 KB
testcase_20 AC 1,205 ms
104,880 KB
testcase_21 AC 1,204 ms
105,140 KB
testcase_22 AC 1,206 ms
104,448 KB
権限があれば一括ダウンロードができます

ソースコード

diff #

#yukicoder 2303 Frog on Grid

#MODnCr計算機(行数削減版)
class MODnCr:
    def __init__(self,fact_N,MOD,invN=1000):
        self._N=fact_N; self._invN=invN; self._MOD=MOD; self._fact=[1]*(self._N+1); self._inv=[1]*(self._invN+1); self._finv=[1]*(self._N+1)
        for i in range(2,self._N+1): self._fact[i]=self._fact[i-1]*i%self._MOD
        for i in range(2,self._invN+1): self._inv[i]=-self._inv[self._MOD%i]*(self._MOD//i)%self._MOD
        for i in range(2,min(self._invN,self._N)+1): self._finv[i]=self._finv[i-1]*self._inv[i]%self._MOD
        self._finv[self._N]=pow(self._fact[self._N],self._MOD-2,self._MOD)
        for i in range(self._N-1,self._invN,-1): self._finv[i]=self._finv[i+1]*(i+1)%self._MOD
    def _update(self,N):
        if N<=self._N: return 0
        dist=N-self._N; self._fact.extend([1]*dist); self._finv.extend([1]*dist)
        for i in range(self._N+1,N+1): self._fact[i]=self._fact[i-1]*i%self._MOD
        self._finv[N]=self.modinv(self._fact[N])
        for i in range(N-1,self._N,-1): self._finv[i]=self._finv[i+1]*(i+1)%self._MOD
        self._N=N; return 1
    def nCr(self,n,r):
        if self._N<n: self._update(n)
        return 0 if any([n<r,n<0,r<0]) else self._fact[n]*self._finv[n-r]%self._MOD*self._finv[r]%self._MOD
    def modinv(self,x): return self._inv[x] if x<=self._invN else (-self._inv[self._MOD%x]*(self._MOD//x))%self._MOD if x> self._invN>=self._MOD%x else pow(x,self._MOD-2,self._MOD)

#MOD = 998244353 にのみ対応したFFT。それ以外では機能しません。
class NTT_998244353:
    def __init__(self,MOD=998244353): self._MOD=998244353
    def _FFT(self,f,fft_len,IDFT=False):
        h=0
        while 2**h < max(len(f),fft_len): h+=1
        f+=[0]*(2**h - len(f)); P=pow(3,119*2**(23-h),self._MOD)
        if IDFT: P=pow(P,2**h-1,self._MOD); rev=pow(2**h,self._MOD-2,self._MOD)
        for i in range(2**h):  #バタフライ演算の並び替え
            j=0
            for k in range(h): j|=(i>>k&1)<<(h-1-k)
            if i<j: f[i],f[j]=f[j],f[i]
        for x in range(h):
            b=2**x; Q=pow(P,2**(h-x-1),self._MOD); W=1  #W=Q^j
            for j in range(b):
                for k in range(0,2**h,2*b):
                    s,t=f[j+k],f[j+k+b]*W%self._MOD; f[j+k]=(s+t)%self._MOD; f[j+k+b]=(s-t)%self._MOD
                W=W*Q%self._MOD
        if IDFT:
            for i in range(2**h): f[i]=f[i]*rev%self._MOD
        return f
    def convolve(self,f,g):
        N=1; L=len(f)+len(g)-1
        while N<L: N*=2
        f=self._FFT(f,N); g=self._FFT(g,N); h=[f[i]*g[i]%self._MOD for i in range(N)]
        return self._FFT(h,N,True)[:L]


H,W=map(int,input().split()); MOD=998244353
nCr=MODnCr(4*10**5+1,MOD,2*10**5+1); NTT=NTT_998244353()
DPh=[0]*(H+1); DPw=[0]*(W+1)
for h in range(H+1):
    x=2*h-H; y=h-x; DPh[h]=nCr._finv[x]*nCr._finv[y]%MOD if 0<=x and 0<=y else 0
for w in range(W+1):
    x=2*w-W; y=w-x; DPw[w]=nCr._finv[x]*nCr._finv[y]%MOD if 0<=x and 0<=y else 0
DP=NTT.convolve(DPh,DPw)
for i in range(1,len(DP)): DP[0]+=DP[i]*nCr._fact[i]%MOD
print(DP[0]%MOD)
0