动态规划解决“最大子数组”问题
2014-11-14 00:17
253 查看
TODO: 动态规划到底是个什么玩艺?
ref:http://www.cnblogs.com/waytofall/archive/2012/04/10/2439820.html
I 只考虑怎样产生更大的子组和:
假设处理到第i个节点时:
1. 考虑是否i节点是否可使子组的和变大
a) 如果i节点大于0,则最大子组和是前面求到的数组和 加上 i节点值
b) 如果i节点小于0(等于0的话,值可以带上i,也可以不带上i,无所谓),当最大子数组的和是前面求的子组和
2. 然后考虑最大值是否应该更新了
a) 如果当前子组和大于最大和,则更新
int // 动态规划法
get_max_sub(int a[], int len)
{
int max_sum, cur_sum;
int i;
max_sum = cur_sum = a[0];
i = 0;
while (++i < len) {
if (cur_sum > 0) {
cur_sum += a[i];
} else {
cur_sum = a[i];
}
if (cur_sum > max_sum) {
max_sum = cur_sum;
}
}
return max_sum;
}
II 再细化考虑子数组的前后边界
1. 因为子数组和是负时,则最大值就是i节点,则将左边界挪到i节点上。
2. 当i节点为负,(思维雷区!!),到于右边办什么时挪?当然是子数组和变大了再挪了(子和变大了,子数组扩张了)
int // 动态规划法
get_max_sub(int a[], int len, int <, int &rt)
{
int max_sum, cur_sum;
int i;
max_sum = cur_sum = a[0];
lt = rt = 0;
i = 0;
while (++i < len) {
if (cur_sum > 0) {
cur_sum += a[i];
} else {
cur_sum = a[i];
lt = i;
}
if (cur_sum > max_sum) {
max_sum = cur_sum;
rt = i;
}
}
return max_sum;
}
总结:
1. 思维深度一点点加深,由少及多
2. 摆脱思维惯性,避开雷区。
考虑最大子数组时,考虑的中心是历史子数组和是正还是负(即子数组和是当前第个i节点呢还是第i个节点加上以前的和呢),而不是只考虑加上i节点子数组是变大还是变小(直观/惯性思维引入雷区)
ref:http://www.cnblogs.com/waytofall/archive/2012/04/10/2439820.html
I 只考虑怎样产生更大的子组和:
假设处理到第i个节点时:
1. 考虑是否i节点是否可使子组的和变大
a) 如果i节点大于0,则最大子组和是前面求到的数组和 加上 i节点值
b) 如果i节点小于0(等于0的话,值可以带上i,也可以不带上i,无所谓),当最大子数组的和是前面求的子组和
2. 然后考虑最大值是否应该更新了
a) 如果当前子组和大于最大和,则更新
int // 动态规划法
get_max_sub(int a[], int len)
{
int max_sum, cur_sum;
int i;
max_sum = cur_sum = a[0];
i = 0;
while (++i < len) {
if (cur_sum > 0) {
cur_sum += a[i];
} else {
cur_sum = a[i];
}
if (cur_sum > max_sum) {
max_sum = cur_sum;
}
}
return max_sum;
}
II 再细化考虑子数组的前后边界
1. 因为子数组和是负时,则最大值就是i节点,则将左边界挪到i节点上。
2. 当i节点为负,(思维雷区!!),到于右边办什么时挪?当然是子数组和变大了再挪了(子和变大了,子数组扩张了)
int // 动态规划法
get_max_sub(int a[], int len, int <, int &rt)
{
int max_sum, cur_sum;
int i;
max_sum = cur_sum = a[0];
lt = rt = 0;
i = 0;
while (++i < len) {
if (cur_sum > 0) {
cur_sum += a[i];
} else {
cur_sum = a[i];
lt = i;
}
if (cur_sum > max_sum) {
max_sum = cur_sum;
rt = i;
}
}
return max_sum;
}
总结:
1. 思维深度一点点加深,由少及多
2. 摆脱思维惯性,避开雷区。
考虑最大子数组时,考虑的中心是历史子数组和是正还是负(即子数组和是当前第个i节点呢还是第i个节点加上以前的和呢),而不是只考虑加上i节点子数组是变大还是变小(直观/惯性思维引入雷区)
相关文章推荐
- 利用动态规划解决实际问题之多次兑换获取最大外汇收益
- 最大子数组问题【动态规划】
- PHP实现求连续子数组最大和问题2种解决方法
- 最大子数组问题(动态规划)--【算法导论】
- c#数据结构之最大子数组问题(暴力解决法)
- 【软件工程】解决求数组的子数组最大和问题
- 0-1背包问题,用滚动数组,动态规划解决
- HDU 1024 Max Sum Plus Plus(动态规划,给定一个数组,求其分成m个不相交子段和最大值的问题)
- 分治法解决最大子数组问题
- 分治法解决寻找数组中最大最小值的问题
- 利用数组作参数求最大值(感觉学了数组能很快的解决问题)
- 分治策略解决最大子数组问题
- PKU 1050 动态规划-解决最大子矩阵问题
- Leetcode121.+Leetcode53. Kadane算法解决最大子数组问题
- 动态规划求解连续子数组最大和问题(应该是新的描述方法?)
- 【Leetcod 动态规划】 子数组最大和一类的问题
- 分治策略__解决最大连续子数组的问题
- 分治法解决最大子数组问题 (C/C++)
- 分治法解决最大子数组问题
- 最大子数组问题(动态规划)--【算法导论】