最大子段和(dp)

2021-10-02 13:33:27 字數 2463 閱讀 8974

最基礎的的最大子段和,設dp[

i]

dp[i]

dp[i

]為以num

[i

]num[i]

num[i]

結尾的最大子段和,有dp[

i]=m

ax(d

p[i−

1]+n

um[i

],nu

m[i]

)dp[i]=max(dp[i-1]+num[i],num[i])

dp[i]=

max(

dp[i

−1]+

num[

i],n

um[i

]),最終結果即為max

(dp[

i]

)max(dp[i])

max(dp

[i])

#include

#include

#include

#include

#include

#include

#include

using namespace std;

int a[

10001];

tuple<

int,

int,

int>

solve

(int a,

int n)

else

if(maxans(maxans<0)

return

make_tuple

(maxans,ansbeg,ansend);}

intmain()

return0;

}

這個好難= =

題意是將乙個長度為n的序列,分成m段不相交叉的子段,使得他們的和最大,m=1時就是最基礎的最大子段和。

於是可以用dp[

i][j

]dp[i][j]

dp[i][

j]來表示在前j個數中,以num

[j

]num[j]

num[j]

結尾並分為i段的最大和。此時我們可以得出如下遞推式

d p[

i][j

]=ma

xdp[i][j]=max\

dp[i][

j]=m

ax其中

\表示n um

[j

]num[j]

num[j]

單獨分成一段,然後將i

ii到j−1

j-1j−

1分成i−1

i-1i−

1段,dp[

i][j

−1]+

num[

j]

dp[i][j-1]+num[j]

dp[i][

j−1]

+num

[j]則表示將num

[j

]num[j]

num[j]

加入到以num

[j−1

]num[j-1]

num[j−

1]結尾的那一段中。

這題是2023年南京大學計算機系本科生開放日機試第一題,由於限制只有100直接暴力列舉o(n

4)

o(n^4)

o(n4

)即可。

poj1050網上的題解參差不齊,因為只限制100,一堆o(n

4)

o(n^4)

o(n4

)的題解還美其名曰dpdp

dp,o (n

4)

o(n^4)

o(n4

)直接暴力不香嗎,此處百練的鏈結資料限制提高到500,o(n

4)

o(n^4)

o(n4

)會超時,需要o(n

3)

o(n^3)

o(n3)的dpdp

dp思想就是求矩陣行和,化成一維,然後求最大子段和

#include

#include

#include

#include

#include

#include

#include

using namespace std;

//最大子段和

intgetmaxsubsum

(int a,

int n)

return maxans;

}const

int max_len=

501;

int mat[max_len]

[max_len]

;int tem[max_len]

;int

main()

}printf

("%d\n"

,ans);}

return0;

}

最大子段和 (dp

n個整數組成的序列a1,a2,a3,ann,求該序列如ai ai 1 aj的連續子段和的最大值。當所給的整數均為負數時和為0。例如 2,11,4,13,5,2,和最大的子段為 11,4,13。和為20。第1行 整數序列的長度n 2 n 50000 第2 n 1行 n個整數 10 9 ai 10 9 ...

dp 最大子段和

注意 在實際問題中可能題目要求至少選乙個,可能可以乙個都不選 只返回最大子段和 include include using namespace std const int maxn 2e5 10 const int inf 0x7fffffff int n int a maxn int maxsum...

最大子段和 經典dp

n個整數組成的序列a11,a22,a33,ann,求該序列如aii ai 1i 1 ajj的連續子段和的最大值。當所給的整數均為負數時和為0。例如 2,11,4,13,5,2,和最大的子段為 11,4,13。和為20。input 第1行 整數序列的長度n 2 n 50000 第2 n 1行 n個整數...