1. 程式人生 > >C. George and Job

C. George and Job

C. George and Job

題目連線
這是一道二維的dp。
題目的大致意思為給你n個數,每一段有m個數,取k段,並且每一段區間沒有交叉。資料型別要用long long。
用sum陣列記錄字首和,dp[i][]j]中i表示到第i個數時取了j段區間的最大和。
dp[i][j]可以由dp[i-1][j]沒有新增區間得到,也可以由dp[i-m][j-1]添加了一段區間得到。所以得到的狀態轉移方程為dp[i][j]=max(dp[i-1][j],dp[i-m][j-1]+sum[i]-sum[i-m];

#include<stdio.h>
#include<string.h>
#include<iostream>
#include<algorithm>
using namespace std;
typedef long long ll;
ll sum[5500],dp[5500][5500],a;
int main()
{
    ll n,m,k,i,j;
    scanf("%lld %lld %lld",&n,&m,&k);
    memset(sum,0,sizeof(sum));
    memset(dp,0,sizeof(dp));
    for(i=1; i<=n; i++)
    {
        scanf("%lld",&a);
        sum[i]=a+sum[i-1];
    }
    for(i=1; i<=n; i++)
        for(j=1; j<=k; j++)
            if(i-m>=0)
                dp[i][j]=max(dp[i-1][j],dp[i-m][j-1]+sum[i]-sum[i-m]);
    printf("%lld\n",dp[n][k]);
    return 0;
}

這是自己第一次寫部落格,有不對的地方請多多指教。