トピック:https://atcoder.jp/contests/agc002/tasks/agc002_f
IFFプレフィックス番号0> =いくつかの色。
デザインDPは、完了したと考えているカラーポイントのすべての色を置くために時間をかけ、一つ一つを入れないでください。だから、「古いカラーポイントの左側、利用可能であるどれだけ」考えていません。
満たされたどのように多くの位置を知っている新しいリリースの色は、すべての色点への配置プログラムの数がカウントされます。
DP [i]の[j]は、i番目のプット0、j個のカラースキームを示しています。私は色が順番に入れ、最後に階乗を掛けていると思います。そこ\(DP [I] [J] - > DP [I + 1] [j]は、DP [I] [J] * \ binom {(NJ)(K-1)+ NI-1、K-2 } - > DP [I]、[J + 1] \)。
書式#include <cstdioを> する#include <CStringの> の#include <アルゴリズム> に#define LL長い長い 使って 名前空間はstdを、 CONSTの INT N = 2005、M = N * N、MOD = 1E9 + 7 。 INT UPT(INT X) { 一方(X> = MOD)X- = MOD。一方、(x < 0)、X + = MOD。戻りX;} int型 PW(int型のx、int型K) { int型 RET = 1。一方、(K){ 場合(K&1* X%MOD RET)RET =(LL); X =(LL)X * X%MOD; >> = K 1 ;} 戻りRET;} int型N、K、JC [M]、JCN [M]、DP [N] [N]。 ボイドのinit() { int型 LM = N * K。 JC [ 0 ] = 1。用(int型 I = 1 ; I <= LM; I ++)は、JC [I] =(LL)JC [I- 1 ] * I%MOD。 JCN [LM]は(JC [LM]、mod- PW = 2 )。 以下のために(int型 iは= LM- 1 ; I> = 0 ; I - )JCNを[I] =(LL)JCN [I + 1 ] *(I + 1)%MOD。 } int型C(INT nは、INT M) { 場合(N < 0 || M < 0 || N <M)戻り 0 ; リターン(LL)JC [N] * JCN [M]%MOD * JCN [nm]の%MOD。 } int型のmain() { scanf関数(" %D%dの"、&N&K)。もし(Kの== 1){プット(" 1 ")。戻り 0 ;} のinit(); DP [ 0 ] [ 0 ] = 1 。 以下のための(int型 I = 0; iが<= N; I ++ ) のための(INT J = 0 ; J <= I; J ++ ) { 場合(DP [I] [J])!続けます。int型 TP = DP [I] [J]。 場合 DP [I +(iがN <)1 ] [J] = UPT(DP [I + 1 ] [J] + TP)を、 もし(J < I) { int型ミリリットル= C((NJ)*(K- 1)+ NI- 1、K- 2 )。 DP [I]、[J + 1 ] =(DP [I]、[J + 1 ] +(LL)ミリリットル* TP)%MOD。 } } のprintf(" %LLDする\ n "、[N](LL)DP [N] * JC [N]%のMOD)。 リターン 0 ; }