您的位置:首页 > 其它

hdu 1087 Super Jumping! Jumping! Jumping!

2013-04-18 16:50 375 查看
此题用简单dp解决,最长上升子序列和。

问题思考: 对某一个数,它是还是不是最大子序列和里的一位,我们设一个数组dp[],

dp[i]就表示以第i个数为最后一位的前1到i个数中的最长子序列的总和(注意这个最长是指以第i个数结尾的子序列中最长的)。

这样我们很快就能想到,要算dp[i+1]时,即要求出以第i+1个数为末位的前1到i+1个数中最长的子序列和。

就是拿第i+1个数与前面所有小于第i+1个数的值的dp数组的值相加,保存其中最大的一个就可以了。

因为对于dp[k] (k < i+1) 第k个数只要小于第i+1个数,那么也就意味着这个子序列可以更长更大。

可以看出根据这个算法,在所有元素都有序的情况下,时间复杂度最大。达到了O(n^2).

贴上码:

#include <string.h>
#include <stdio.h>

#define N 1001

int dp
;

int main()
{
int T,j,i,max,t;
int a
;
while(scanf("%d",&T),T){
memset(a,0,sizeof(a));
for(i = 1; i <= T; i++){
scanf("%d",&a[i]);
}
memset(dp,0,sizeof(dp));
max = -1;
for(i = 0; i <= T; i++){
t = 0;
for(j = 0; j < i; j++){
if(a[i] > a[j]){
if( t < dp[j])
t = dp[j];
}
}
dp[i] = t + a[i];
if(dp[i] > max)max = dp[i];
}
printf("%d\n",max);
}
return 0;
}

#include <iostream>
#include <stdio.h>
#include <string.h>
#include <math.h>
#include <stdlib.h>
#include <map>
#include <set>
#include <vector>
#include <stack>
#include <algorithm>

using namespace std;

#define mst(a,b) memset(a,b,sizeof(a))
#define eps 10e-8

const int MAX_ = 1010;
const int N = 100010;
const int INF = 0x7fffffff;

int a[MAX_], dp[MAX_];

int main(){
int n, cnt, k, res;
while(scanf("%d",&n), n){
for(int i = 1; i <= n; ++i){
scanf("%d",&a[i]);
}
int ans = -INF;
for(int i = 1; i <= n; ++i){
dp[i] = a[i];
for(int j = 1; j < i; ++j){
if(a[i] > a[j]){
dp[i] = max(dp[i], dp[j] + a[i]);
}
}
ans = max(ans,dp[i]);
}
printf("%d\n",ans);
}
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: