問題の解決策
- (0,0)から(M、N)にランダムウォークシナリオC(N + M、M)の数であります
- その後、被験者の要件は、Y = Xの行を渡すことができない、すなわち、Y = X + 1に手を触れないで直線状であります
- 我々は、次に、(N、M)は、過去の対称点である(M-1、N + 1)= X + 1つの対称経過Yに沿って不正経路を検討します
- 我々は対称の原点から行く見出さ(M-1、N + 1、証明番号カタロニア語を考える ) バックパス対称であってもよいし、原点からの1つに対応する終了するY通過(N、M)= X定額パス
- したがって、Y = Xを通る経路の端部に原点からのパスの数が対称的である、すなわちC(N + 1 + M-1、M-1)= C(N + M、M-1)
- すべての答えはC(N + M、M)= C(N + M、M-1)であります
- 式には、それを簡略化することができます。
- 共通分母は:
- 最後に、[OK]で精度を作ります
コード
1の#include <cstdioを> 2の#include <CStringの> 3の#include <アルゴリズム> 4 使って 名前空間STDを、 5 のconst int型 N = 10000、M = N * 10 。 6 構造体NUM 7 { 8 int型集[N]。 9 友達NUMの演算子 - (NUM yを、num個のZ) 10 { 11 NUM X;のmemset(x.shu、0、はsizeof(x.shu))、x.shu [ 0 ] = y.shu [ 0 ]。 12 のための(int型 I = 1 ; I <= x.shu [ 0 ]; iが++ ) 13 { 14 x.shu [I] + = y.shu [I] - z.shu [I]。 15 であれば(x.shu [I] < 0)x.shu [I] + = M、x.shu [I + 1 ] - 。 16 } 17 ながら(x.shu [x.shu [!0 ])x.shu [ 0 ] - 。 18 リターンX。 19 } 20 フレンドNUMの演算子 *(NUM yを、int型Z) 21 { 22 NUM X;のmemset(x.shu、0、はsizeof(x.shu))、x.shu [ 0 ] = y.shu [ 0 ]。 23 のために(int型 I = 1 ; I <= x.shu [ 0 ]; iが++)x.shu [I] + = y.shu [I] * Z、x.shu [I + 1 ] + = x.shu [ i]は/M,x.shu [I]%= M。 24 一方(x.shu [x.shu [ 0 ] + 1 ])x.shu [ 0 ] ++ ; 25 リターンX。 26 } 27 } ANS。 28 int型 P [N + 5 ]、C [N + 5 ]、N、M。 29 ボイド RECOUT(int型のx、int型 F){ ための(X =!1であり、x / = P [X])C [Pの[X] + = F。} 30 NUM C(INT M、int型N) 31 { 32 NUM X;のmemset(x.shu、0、はsizeof(x.shu))、x.shu [ 0 ] = x.shu [ 1 ] = 1、memsetを(C、0、はsizeof (c)参照)。 33 のためには、(int型、I = N + 1 ; I <= M; iは++)RECOUT(I、1 )。 34 のための(int型I = 1 ; I <= MN; i)はRECOUT(I ++ - 1 )。 35 のために(int型 i = 1 ; iが= Nを<; I ++)のための(INT J = 1 ; J <= C [i]は、J ++)、X = X * iは、 36 リターンX。 37 } 38 のint main()の 39 { 40 のために(int型 I = 2 ; iは= N <、iは++)場合(P [i]が!の)のための(int型 J = 1 ; J <= N / I、J ++)は、P [私はjは*] = I; 41 のscanf(" %D%D"&N、&M)、ANS = C(M + N、M)-C(m + nは、M- 1)のprintf(" %dの」、ans.shu [ans.shu [ 0 ]]); 42 用(INT I = ans.shu [ 0 ] - 1 ; iは> = 1 ; i--)のprintf(" %の05D " ans.shu、[I]); 43 }