• POJ 2479 Maximum sum (动态规划)


    POJ 2479 Maximum sum,题目大意是:对于给定的整数序列A={a1, a2,..., an},我们如下定义函数 d(A):


    我们的目标就是求出d(A)

    解决方案:
    这个题目是一个典型的动态规划题目,我们可以这样看,d(A)最大,即两个子序列之和最大,而这两个子序列是不相交的,因而我们可以将题目转换为如下形式:
    第一步,对于位置i,求i左边序列(可以包含i)的最大值和i右边序列的最大值。在程序中分别用leftMax和rightMax数组进行保存。
    第二步,然后对i取不同的值,即遍历i,得到d(A)。

    如对于序列A = {1 -1 2 2 3 -3 4 -4 5 -5},我们对于A[0],求其左边序列(就是它自己)的最大值和它右边序列的最大值,然后相加,保存相应的值d。
    然后对于A[1],求其左边序列的最大值和右边序列的最大值,然后相加,和上次计算的出来的d比较,若大,则保存之,若小,则废弃之。
    ......
    依次循环下去

    在上述过程中,我们还会总结出一个规律,当我们遍历 i 来计算leftMax时,需要一个数组left来保存“包含input[i]的连续序列的和的最大值”,这个解释一下,如序列 input = {1,1,-6,-3,5,4},当 i 为3,即扫描到input[3] = -3时,这时我们来求left[3],我们发现包含input[3]的连续序列的和的最大值为-3,即这个序列就是其自己。而对于left[2]来说,left[2] = -4,即这个序列为{1,1,-6}。

    我们就用input = {1,1,-6,-3,5,4}来扫描一遍,

    i = 0,input[0] = 1,left[0] = 1,leftMax[0] = 1;

    i = 1,input[1] = 1,left[1] = 1 + 1 = 2,leftMax[1] = 2;

    i = 2,input[2] = -6,left[2] = 1 + 1 + -6 = -4,leftMax[2] = 2;

    i = 3,input[3] = -3,left[3] = -3,leftMax[3] = 2;

    i = 4,input[4] = 5,left[4] = 5,leftMax[4] = 5;

    i = 5,input[5] = 4,left[5] = 9,leftMax[5] = 9;

    结合代码走一遍就会明白整个过程了。

    代码如下:

     1 #include <stdio.h>  
     2 #define LEN 50000
     3 int main()
     4 {
     5     int input[LEN];
     6     int left[LEN];
     7     int right[LEN];
     8 
     9     int leftMax[LEN];
    10     int rightMax[LEN];
    11 
    12     int max = -500000000;
    13 
    14     int cases;
    15     int n;
    16     scanf("%d", &cases);
    17 
    18     while(cases--)
    19     {
    20         scanf("%d", &n);
    21         if(n < 2)
    22             break;
    23         int i;
    24         for(i = 0; i < n; i++)
    25         {
    26             scanf("%d", &input[i]);
    27             if(i == 0)
    28             {
    29                 left[0] = input[0];
    30                 leftMax[0] = left[0];
    31                 if(leftMax[0] > max)
    32                     max = leftMax[0];
    33             }
    34             else
    35             {
    36                 if(left[i - 1] < 0)
    37                 {
    38                     left[i] = input[i];
    39                     if(left[i] > max)
    40                         max = left[i];
    41                     leftMax[i] = max;
    42                 }
    43                 else
    44                 {
    45                     left[i]  = input[i] + left[i-1];
    46                     if(left[i] > max)
    47                         max = left[i];
    48                     leftMax[i] = max;
    49                 }
    50             }
    51         }
    52         max = -500000000;
    53         for(i = n - 1; i >=0; i--)
    54         {
    55             if(i == n - 1)
    56             {
    57                 right[i] = input[n-1];
    58                 rightMax[i] = right[i];
    59                 if(rightMax[i] > max)
    60                     max = rightMax[i];
    61             }
    62             else
    63             {
    64                 if(right[i + 1] < 0 )
    65                 {
    66                     right[i] = input[i];
    67                     if(right[i] > max)
    68                         max = right[i];
    69                     rightMax[i] = max;
    70                 }
    71                 else
    72                 {
    73                     right[i] = input[i] + right[i + 1];
    74                     if(right[i] > max)
    75                         max = right[i];
    76                     rightMax[i] = max;
    77                 }
    78             }
    79         }
    80         max = -500000000;
    81 
    82         if(n == 2)
    83             max = input[0] + input[1];
    84         else
    85         {
    86             for(i = 0; i < n - 1; i++)
    87             {
    88                 if((leftMax[i] + rightMax[i+1]) > max)
    89                     max = leftMax[i] + rightMax[i+1];
    90             }
    91         }
    92 
    93         printf("%d\n", max);
    94         max = -500000000;
    95     }
    96     return 0;
    97 }
  • 相关阅读:
    Java AbstractQueuedSynchronizer(AQS)
    CentOS Install Rancher & K3s
    CentOS Install Rancher & Kubernetes
    CentOS Install Kubernetes & Kubesphere
    支付宝小程序入门
    uni-app 抽奖
    APP上架
    uniapp微信小程序语音识别实现
    uniapp 安卓打包之导入的项目打包指导
    uniapp 支付宝 支付后不成功回调
  • 原文地址:https://www.cnblogs.com/null00/p/2570561.html
Copyright © 2020-2023  润新知