问题 D: Mountain Climbing

时间限制: 1 Sec  内存限制: 64 MB
提交 状态

题目描述

Farmer John has discovered that his cows produce higher quality milk when they are subject to strenuous exercise.  He therefore decides to send his N cows (1 <= N <= 25,000) to climb up and then back down a nearby mountain!

Cow i takes U(i) time to climb up the mountain and then D(i) time to climb down the mountain.  Being domesticated cows, each cow needs the help of a farmer for each leg of the climb, but due to the poor economy, there are only two farmers available, Farmer John and his cousin Farmer Don.  FJ plans to guide cows for the upward climb, and FD will then guide the cows for the downward climb.  Since every cow needs a guide, and there is only one farmer for each part of the voyage, at most one cow may be climbing upward at any point in time (assisted by FJ), and at most one cow may be  climbing down at any point in time (assisted by FD).  A group of cows may temporarily accumulate at the top of the mountain if they climb up and then need to wait for FD's assistance before climbing down.  Cows may climb down in a different order than they climbed up.

Please determine the least possible amount of time for all N cows to make the entire journey.
 

输入

* Line 1: The number of cows, N.
* Lines 2..1+N: Line i+1 contains two space-separated integers: U(i) and D(i).  (1 <= U(i), D(i) <= 50,000).

输出

* Line 1: A single integer representing the least amount of time for all the cows to cross the mountain.
 

样例输入 Copy

3
6 4
8 1
2 3

样例输出 Copy

17
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
///上山比下山快的,先上山
///
struct node
{
    ll u,d;
} nd[25005];
bool cmp(node a,node b)
{
    ///最后总时间是up(1)+..+up(k)+down(m)...+down(n)
    ///保证上面加的时间up和down尽量小
    if(a.u>=a.d&&b.u>=b.d)
        return a.d>b.d;
    else if(a.u<a.d&&b.u<b.d)
        return a.u<b.u;
    else return a.u*b.d<a.d*b.u;

}
priority_queue<ll,vector<ll>,greater<ll> >q;
///priority_queue<int>q;
///从大到小排序
int main()
{
    int n;
    scanf("%d",&n);
    for(int i=1; i<=n; i++)
    {
        scanf("%lld%lld",&nd[i].u,&nd[i].d);
    }
    sort(nd+1,nd+1+n,cmp);
    ll s=nd[1].u;
    ll x=nd[1].u+nd[1].d;
    for(int i=2; i<=n; i++)
    {
        s+=nd[i].u;
        if(s<=x)///上山时间<下山时间,说明在山顶等着
        {
            x=x+nd[i].d;
        }
        else///上山时间大于下山时间,说明要等到上山了才能下山
        {
           x=s+nd[i].d;
        }
    }

    printf("%lld\n",x);
    return 0;
}

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值