hdu 1024

HDU 1024
一道典型的的动态规划题目,重点在与找到一种正确的状态规划方法,然后建立不同状态间转换的方程式。
题意大致如下:给你n个数,要你在这n个数中取m段数(每段无交集),使这m段之和最大。
每次输入格式:m,n,a1,a2,....an。
一直读到文件尾。
状态方程转换公式:dp[i][j]=max(dp[i][j-1]+arr[j] , max(dp[i-1][k])+arr[j])。(k<j)
可以这样理解,dp[i][j]是以第j个数结尾(包含j)取i段数时能得到的最大和,分两种状态能完全的包含每个情况,一是当第j个数不是单独成段(dp[i][j-1]+arr[j]),二是第j个数单独成段(max(dp[i-1][k])+arr[j])。这样考虑合理的原因就不解释了,看着公式很好想。
然后就是两个细节吧,一是数组存放,要用滚动数组,不然存不下来。(从dp[i][0]到dp[i][n]其实只用存上一个状态数组),二是max(dp[i-1][k]),因为用了滚动数组,所以我们只有dp[x][j-1]的数据。于是我们可以用一个maxnn[x]的数组来记录目前得到的取x段能达到的最大和的值。(1<=x<=m)这样不仅记录了我们所需要的数据,而且每次计算时也节省了时间(因为maxnn[i-1]==max(dp[i-1][k]) )。注意每次计算完一轮dp[k][j]后更新maxnn[x]就好。
代码如下:
#include<iostream>
#include<cmath>
#include<cstdio>
#include<cstring>
using namespace std;
const int maxn=1e6+10;
const int inf=0x08080808;
int arr[maxn];
int f[maxn];
int maxnn[maxn];
int Max(int a,int b){
    return a>b?a:b;
}
int sum(int n){
    int ans=0;
    for(int i=1;i<=n;++i)
        ans+=arr[i];
    return ans;
}
int main(){
    int m,n;
    while(scanf("%d%d",&m,&n)!=EOF){
        for(int i=1;i<=n;++i)
            scanf("%d",&arr[i]);
        for(int i=1;i<=m;++i)
            maxnn[i]=-inf;
        f[1]=arr[1];
        maxnn[1]=arr[1];
        maxnn[0]=0;
        for(int i=2;i<=n;++i){
            for(int j=1;j<=m;++j){
                if(j==i){
                    f[j]=sum(j);
                    break;
                }
                f[j]=Max(f[j]+arr[i],maxnn[j-1]+arr[i]);
            }
            for(int k=1;k<=m;++k){
                if(k>i) break;
                if(f[k]>maxnn[k])
                    maxnn[k]=f[k];
            }
        }
        printf("%d\n",maxnn[m]);
    }
    return 0;
}


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
经导师精心指导并认可、获 98 分的毕业设计项目!【项目资源】:微信小程序。【项目说明】:聚焦计算机相关专业毕设及实战操练,可作课程设计与期末大作业,含全部源码,能直用于毕设,经严格调试,运行有保障!【项目服务】:有任何使用上的问题,欢迎随时与博主沟通,博主会及时解答。 经导师精心指导并认可、获 98 分的毕业设计项目!【项目资源】:微信小程序。【项目说明】:聚焦计算机相关专业毕设及实战操练,可作课程设计与期末大作业,含全部源码,能直用于毕设,经严格调试,运行有保障!【项目服务】:有任何使用上的问题,欢迎随时与博主沟通,博主会及时解答。 经导师精心指导并认可、获 98 分的毕业设计项目!【项目资源】:微信小程序。【项目说明】:聚焦计算机相关专业毕设及实战操练,可作课程设计与期末大作业,含全部源码,能直用于毕设,经严格调试,运行有保障!【项目服务】:有任何使用上的问题,欢迎随时与博主沟通,博主会及时解答。 经导师精心指导并认可、获 98 分的毕业设计项目!【项目资源】:微信小程序。【项目说明】:聚焦计算机相关专业毕设及实战操练,可作课程设计与期末大作业,含全部源码,能直用于毕设,经严格调试,运行有保障!【项目服务】:有任何使用上的问题,欢迎随时与博主沟通,博主会及时解答。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值