スチューデントのキャンプCodeForces - 708E(DP、接頭辞および最適化)

効果:の$ n $の$ M $列の煉瓦列左側境界日$ Pの$確率が破壊され、各ブロックは、夕方の右端には、$ pが$確率、必要な最終的な上限および下限を通信する確率が破壊されていました。

 

$最初の行に$のT $トラバースとして$ {DP} _ {I、L、R}(注)、レンガの最初の行は、$ T $ $ [L、R] $確率の範囲です。

$ {DP} _ {I、ある L、R} = P_ {L、R} \和{DPは} $は({I-1、L 'R '} _ $ [L'、R']満たすために $をそして$ [L、R] $が交差)

$ P_ {L、R} $ $ K $日、残りのタイルは、$ [L、R] $確率いる表します。

二次元の最適化プレフィックスを考える、$ F_ {I、L、Rで示さ 、} = \和\ limits_ {1 \ルX \ルL} \和\ limits_ {1 \ルY \ルR} {DP} _ {IをX、Y} $、  そこに

$$ \ {整列} {DP} _ {I、L、R}&= P_ {L、R}(F_ {I-1、M、R} + F_ {I-1、R、M} -f_始まります{I-1、M、L-1} -f_ {I-1、R、R})\ notag \\&= P_ {L、R}(F_ {I-1、R、M} -f_ {I -1、L-1、L-1})\ notag \端{ALIGN} $$

最後に回答が$ F_ {N、M、M} $である尋ねる。しかし、この複雑さは$ O(NM ^ 2)$です

これは、必要な$ fが$値に$ DP $方程式注目することができることは非常に小さいです。

记$ A_ {I、X} = F_ {I、X、M}、B_ {I、X} = F_ {I、X、X} $、有

$$ dp_ {I、L、R} = P_ {L、R}(A_ {I-1、R} -B_ {I-1、L-1})$$

$$ A_ {I、X} = A_ {I、X-1} + \和\ limits_ {X \ルK \ルM} {DP} _ {I、X、K} $$

$$ B_ {I、X} = B_ {I、X-1} + \和\ limits_ {1 \ルK \ルX} {DP} _ {I、K、X} $$

その後、接頭辞の最適化は、それは、$ O(nm)の$の複雑さであります

書式#include <iostreamの> 
の#include <sstream提供> 
する#include <アルゴリズム> 
書式#include <cstdioを> 
する#include <math.h>の
書式#include <設定> 
書式#include <マップ> 
書式#include <キュー> 
の#include <string>に
する#include < string.hの> 
の#include <ビットセット> 
の#define REP(I、N)のために(INT iは=; I <= N; ++ I)
の#define PER(I、N)のための(iはint型= N; I> = A; - I)
の#defineのHRのputchar(10)
の#define PB一back 
の#define LC(O << 1)
の#define RC(LC | 1)
の#define中間((L + R)>> 1)
の#define LS LC、L、中
の#define RSのRC、ミッド+ 1、R用
の#defineは、最初のx 
の#define yの第二
のstd :: IOS IOの#defineを::sync_with_stdio(偽) 
の#define ENDL '\ n'は
#define DB(A)({REP(__ I、1、n)はCOUT << [__ I] <<」「;}時間)
名前空間stdを使用。
typedefの長い長いLL。
typedefのペア<int型、int型> PII。
CONST int型P = 1E9 + 7、INF = 0x3f3f3f3f。
LLのGCD(-1,11,11- b)は{戻りB GCD(B、%のB):;} 
のLL qpow(-1,11,11- n)で{LLのR = 1%P;(%= Pのために、N ; = *%P、N >> = 1)であれば(N - 1)R = R *%のP、リターンR;} 
?LL INV(LL X){X <= 1を返す:INV(P%以下X)*(PP / X)%P;} 
インラインint型RD(){int型のx = 0; CHAR P = GETCHAR();一方、(P < '0' || P> '9')p = GETCHAR() ;一方、(P> = '0' && P <= '9')、X = X * 10 + P-'0' 、P = GETCHAR();戻りX;} 
//ヘッド



のconst int型N = 1E6 + 10、M = 2E3 + 10。
N INT、M、A、B、K。
INTのFAC [N]、IFAC [N]、P [M]、SUF [M]、プリ[M]。
INT A [2] [M]、B [2] [M]、S1 [M]、S2 [M]。

	REP(I、1、N-1)FAC [i]は= FAC [I-1] *(LL)I%のP。
	IFAC [N-1] = INV(FAC [N-1])。
	PER(I、0、N-2)IFAC [I] = IFAC [I + 1] *(iは1LL + 1)%のP。
} 
INT C(整数nは、INTのM){ 
	IF(N <M)戻り0; 
	リターン(LL)FAC [N] * IFAC [M]%のP *のIFAC [nm]の%のP。
} 

int型のmain(){ 
	INIT()。
	CIN >> N >> M >> A >> B >> K。
	INT X =(LL)*のINV(B)%P、Y =(LL)(P + BA)* INV(B)%のP。
	REP(I、1分(M、K + 1))P [I] =(LL)C(K、I-1)* qpow(X、I-1)%のP *はqpow(Y、K-I +1)%のP。
	REP(I、1、M){ 
		SUF [I] =(SUF [I-1] + P [M-I + 1])%のP。
		事前[I] =(PRE [I-1] + P [I])%のP。
	} 
	REP(I、1、m)のA [0] [I] = 1。
	int型CUR = 0; 
	REP(I、1、N){ 
		CUR ^ = 1; 
		REP(K、1、m)のS1 [K] =(S1 [K-1] +(LL)P [M-K + 1] * A [K] [CUR!])%のP。
		REP(K、1、m)とS2 [K] =(S2 [K-1] - (LL)P [K] * B [K-1] [CUR!])%のP。
		REP(X、1、m)の{ 
			[CUR] [X] [CUR] [X-1] =。
			INT RET =(S1 [M] -S1 [X-1])%のP。
			%のP RET =([!CUR] [X-1])* B [X-1] -suf ret-(LL)(SUF [M])。
			[CUR] [X] =([CUR] [X] +(LL)P [X] * RET)%のP。
		} 
		REP(X、1、M){ 
			B [CUR] [X] = B [CUR] [X-1]。
			INT RET =%のP([!CUR]、S2 [X] +(LL)[X] * A [X]をPRE)。
			B [CUR] [X] =(B [CUR] [X] +(LL)P [M-X + 1] * RET)%のP。
		} 
	} 
	int型ANS = B [CUR] [M]。
	(ANS <0)ANS + = Pなら 
	printf( "%d個の\ n"、ANS)。
}

 

 

 

 

おすすめ

転載: www.cnblogs.com/uid001/p/11279175.html