例題 動規 NKOJ 3686 最大子段和

2021-07-12 01:41:19 字數 2078 閱讀 3240

nkoj 3686 最大子段和

時間限制 : - ms 空間限制 : 65536 kb

問題描述

給你乙個包含n個整數的序列,要求從中取出m個不相交的子段,要求這m個子段的和盡肯能大,輸出這個最大和。

例如,n=7,m=2, 序列如下:

-2 1 4 -2 3 -2 3

最優方案取出的兩段為 這兩段的和為9

輸入格式

第一行,兩個整數n和m

第二行,n個空格間隔的整數,表示整數數列

輸出格式

一行,乙個整數,表示所求答案

樣例輸入

7 2

-2 1 4 -2 3 -2 3

樣例輸出

9提示

1<=n <=100,000 1<=m<=300 且 m<=n

數列中的數字範圍[-50000,50000]

思路:

1、階段:從左往右討論每乙個數字。

2、狀態:f[i][j]表示從前j個數中選出i段的最大和,且j必須作為最後一段結尾

3、決策:討論第j個數加不加入第i段中

4、方程:

f[i][j]=a[1]+a[2]+a[3]+a[4]…+a[j] (i==j)

f[i][j]=max (i< j<=n)

//不選a[j]的情況:當討論到a[i]後面的數時,選出的最佳方案可能不包含a[i];

邊界條件:1<=i<=m, i<=j<=n, i-1<=k<=j-1

優化:

1、空間:考慮到本題空間限制64m,所以需使用滾動陣列

改寫方程如下:

f[i&1][j]=max (i< j<=n)

f[i&1][j]=a[1]+a[2]+a[3]+a[4]…+a[j] (i==j)

注意當討論到f[i][j]時,所得的f[i][j]值需要更新best[j]值,但未更新的best[j]值需要在下一迴圈使用,所以使用temp將需要更新的best[j]值存下,等下一迴圈使用完畢後再更新。且當i==m迴圈中最終的temp值即為所求答案。

**:

#include

#include

using

namespace

std;

#define ll long long

const ll inf=1000000000000000000ll;

ll a[100003];

ll f[2][100003],best[100003],qian[100003];

int main()

ll temp;

for(int i=1;i<=m;i++)

} printf("%i64d",temp);

}

第二種解決方案是只用乙個變數temp儲存,但注意i=1時需提前計算,以及最終答案需要單獨尋找

詳見**:

#include

#include

using

namespace

std;

#define ll long long

const ll inf=1000000000000000000ll;

ll a[100003];

ll f[2][100003],qian[100003];

int main()

ll temp;

for(int i=1;i<=n;i++)

for(int i=2;i<=m;i++)

} }

ll ans=-inf;

for(int i=m;i<=n;i++) if(f[m&1][i]>ans) ans=f[m&1][i];//注意i範圍

printf("%i64d",ans);

}

Employment Planning 動規小練

employment planning 原題鏈結 對於當前月份所需人數,和僱傭最大所需人數之間的情況進行討論。由於解雇金額和僱傭金額的存在,會存在一次性僱傭更多的人以減少解雇金額的情況,所以要討論到所需最大人數。include include include include include incl...

2016 7 13 樹形動規

rmq演算法講完沒幾個小時,我們就開始了小紫中的一節 足見這個演算法很重要 樹形動歸 1.焦作一中資訊學oy 2.小黃 資訊學奧賽一本通 3.小紫 演算法競賽入門經典第二版 題型總結 來自資料1 1 加分二叉樹 區間動規 樹的遍歷 2 二叉蘋果樹 二叉樹上的動規 3 最大利潤 多叉樹上的動規 4 選...

序列型動規

d i 中的i表示前i的元素的某種性質。有一排n棟房子,每棟房子要漆成k種顏色中的一種 任何兩棟相鄰的房子不能漆成同樣的顏色 房子i染成第j種顏色的花費是cost i j 問最少需要花多少錢油漆這些房子 輸入 n 3,k 3 cost 14,2,11 11,14,5 14,3,10 輸出 10 房子...