POJ - 2181 - Jumping Cows

本文解析了JumpingCows问题,通过贪心算法实现,关键在于将数值序列中的波峰值相加、波谷值相减以获取最大跳跃值。文章提供了完整的代码示例。

先上题目

Jumping Cows
Time Limit: 1000MS Memory Limit: 65536K
Total Submissions: 6453 Accepted: 3859

Description

Farmer John's cows would like to jump over the moon, just like the cows in their favorite nursery rhyme. Unfortunately, cows can not jump.

The local witch doctor has mixed up P (1 <= P <= 150,000) potions to aid the cows in their quest to jump. These potions must be administered exactly in the order they were created, though some may be skipped.

Each potion has a 'strength' (1 <= strength <= 500) that enhances the cows' jumping ability. Taking a potion during an odd time step increases the cows' jump; taking a potion during an even time step decreases the jump. Before taking any potions the cows' jumping ability is, of course, 0.

No potion can be taken twice, and once the cow has begun taking potions, one potion must be taken during each time step, starting at time 1. One or more potions may be skipped in each turn.

Determine which potions to take to get the highest jump.

Input

* Line 1: A single integer, P

* Lines 2..P+1: Each line contains a single integer that is the strength of a potion. Line 2 gives the strength of the first potion; line 3 gives the strength of the second potion; and so on.

Output

* Line 1: A single integer that is the maximum possible jump.

Sample Input

8
7
2
1
8
4
3
5
6

Sample Output

17

  题意是这样的,给你一系列数字,从某一个数开始,进行这样的操作:奇数步操作加上这个数,偶数步操作减去这个数,对这个数操作以后只可以对后面的数操作,当然后面的数可以选择跳过。求最终可以得到的最大值。
  这一题一开始想会不会是dp,后来觉得像贪心多一点,做法是这样的,我要得到最大值,那么我每一次加上去的都是比较大的数,每一次减的都是比较小的数,这一系列的数的值有升降起伏,每一次都加上波峰的值,每一次都减去波谷的值就可以得到最大的值了。

  如图,从1开始到4之前一直上升,4是波峰,然后到2时是波谷,到了5时又是波峰,所以最大值=4-2+5=6;
  还要注意的是如果到达了数列的末尾,如果此时需要加数,那当然是加上结尾一个数,因为它是结尾附近最大的数;如果是需要减数,则不需要减了,这样可以保持当前值最大。

上代码:

#include <stdio.h>
#include <string.h>
#include <iostream>
#include <utility>
#include <algorithm>
#define MAX 150000+10
using namespace std;

int p[MAX],n;
bool f;

int main()
{
    int i,sum;
    //freopen("data.txt","r",stdin);
    scanf("%d",&n);
    for(i=1;i<=n;i++) scanf("%d",&p[i]);
    f=1;
    sum=0;
    for(i=1;i<=n;i++)
    {
        if(f)
        {
            while(i<n && p[i]<=p[i+1]) i++;
            sum+=p[i];
            f=0;
        }
        else
        {
            while(i<n && p[i]>=p[i+1]) i++;
            if(i<n) sum-=p[i];
            f=1;
        }
    }
    printf("%d\n",sum);
    return 0;
}
2181

 


转载于:https://www.cnblogs.com/sineatos/p/3241994.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值