分割統治、DPは、この配列の維持を確保する必要がDP DP再帰区間[L、R]である場合、配列を維持する以外の配列[L、R]取り除く
メンテナンスが非常に簡単であり、再帰は、第1の右から左区間であります間隔は、再帰的に右に間隔(第1復元)の範囲に参加することを放置し、次いで、追加しました
1つの#include <ビット/ STDC ++ H> 2 使用して 名前空間STDを、 3 の#define N 2005年 4 の#defineオブジェクト指向0x3f3f3f3f 5 の#define半ば(L + R >> 1) 6 INTの N、M、[N * 10 ]、[N * C 10 ]、[N] F、N [FF ]、G [ 21 ] [N]。 7 ボイド追加(int型 L、int型R){ 8が ため(int型 I = 1と、I <= R; iは++ ){ 9 のmemcpy(FF、F、はsizeof (F))。 10 のための(int型 J =0 ; J <Mであり、j ++ ) 11の F [J] =分([J] F、FF [(J + MA [I])%のM] + C [I])。 12 } 13 } 14 空隙 DFS(int型 L、int型の R、int型の){ 15 であれば(L == R){ 16 長い 長のANS = 0 。 17 のために(int型 I = 0 ;私がm <; Iは++ ) 18 場合 ans--([I] == OO F) 。 19 他 ANS + = F [i]は、 20 のprintf("%LLD \ n " 、ANS); 21 リターン; 22 } 23 のmemcpy(G [S]、F、はsizeof (F)); 24 追加(MID + 1 、R); 25の DFS(L、中間、S + 1 )。 26件 のmemcpy(F、G [S] はsizeof (F)); 27 追加(L、MID); 28の DFS(MID + 1、R、S + 1 ); 29 } 30 INT メイン(){ 31 のscanf(" %dの%のD "、&N、&M); 32 のために(int型 I = 1 iが<= N; iが++)のscanf(" %d個の%のD "、および[I]、&C [I])。 33 のmemset(F、OO、はsizeof (F))。 34 F [ 0 ] = 0 。 35の DFS(1、nは、0 )。 36 }