問題:
給定n個整數(可以為負數)的序列(a1 , a2 , …, an),求其最大子段和(連續的某個子串)。
分析:
蠻力法的話,o(n2)
分治法,將序列分為左右兩部分分別求最大子段和,從分界點開始向兩邊分別找最大子段和再合併,取最大即可。複雜度遞推式:t(n) = 2t(n/2) + o(n) = o(nlogn)
動態規劃,最優子結構的構造有點小技巧。
最優子結構:b[j],表示到j結束的所有子段中最大的那個,起始點從1到j都有可能,如果遍歷一遍j,就可以覆蓋所有子問題。(乍一看似乎就是乙個蠻力,但是由於這題子問題間存在遞推關係,相當於用前面計算過的計算新的,正體現動態規劃的本質,空間換時間,減少重複計算)b[j]意味著至少j被選中了。
確定遞推關係:對於j-1而言,有兩種選擇,選(繼續向左擴張子串)或者不選(子串就是a[j]了),也就是說b[j] = max。最終取b中最大的那個即可。
**:
#include using namespace std;
// 計算序列的最大子段和
// 輸入:序列長度n,序列a,子結構矩陣b,結果記錄矩陣c
// 輸出:最大子段和及其長度
int maxsum(int n, int a, int b, int c)else
}// 求最大值
int maxb = -10000,end = -1;
for(int i = 1;i <= n;i++)
}// 輸出結果
for(int i = c[end];i <= end;i++)
cout<複雜度:
時間複雜度:o(n)
空間複雜度:o(n)
動態規劃 最大子段和
給定乙個陣列a a0,a1,a2,an 求陣列中 連續子段之和 的最大值。1 最簡單的演算法 窮舉法 計算所有的連續子段之和,得出最大值 窮舉法 計算所有的子串行和 o n 3 public static int maxsum1 int data max tmp max tmp max return...
動態規劃 最大子段和
題目描述 給出一段序列,選出其中連續且非空的一段使得這段和最大。輸入輸出格式 輸入格式 第一行是乙個正整數nn,表示了序列的長度。第二行包含n個絕對值不大於10000的整數a i,描述了這段序列。輸出格式 乙個整數,為最大的子段和是多少。子段的最小長度為1。輸入輸出樣例 輸入樣例 1 72 4 3 ...
動態規劃 最大子段和
動態規劃 最大子段和 lyk喜歡幹一些有挑戰的事,比如說求區間最大子段和。它知道這個題目有o n 的做法。於是它想加強一下。也就是說,lyk一開始有n個數,第i個數字是ai,它找來了乙個新的數字p,並想將這n個數字中恰好乙個數字替換成p。要求替換後的最大子段和盡可能大。lyk知道這個題目仍然很簡單,...