【poj1857】To Europe! To Europe! DP

Description

Almost everyone in the candidate states wants to `go to Europe”, although most of the people have very vague ideas about what this actually means. Anyway, immediately after the borders are open, the inhabitants will take their cars and trucks and will `go to Europe”. This can cause many troubles, as the roads will be suddenly overloaded by vehicles of various types. You are to help to solve some of these traffic jams.

Assume a convoy of vehicles has lined up in front of a single lane and one-way bridge over a river. Note that since the street is single lane, no vehicle can overtake any other. The bridge can sustain a given maximum load. To control the traffic on the bridge, operators are stationed on either end of the bridge. The convoy of vehicles is to be divided into groups, such that all the vehicles in any group can cross the bridge together. When a group reaches the other side, the operator on that side of the bridge uses a telephone to inform the operator on this side that the next group can start its journey over the bridge.

The weight of each vehicle is known. The sum of the weights of the vehicles in any group cannot exceed the maximum load sustainable by the bridge. Associated with each vehicle is the maximum speed with which it can travel over the bridge. The time taken by a group of vehicles is calculated as the time taken by the slowest vehicle in the group to cross the bridge. The problem is to find the minimum amount of time in which the entire convoy can cross the bridge.

Input

The input consists of several test cases. The first line of each test case contains three positive integers (separated by blanks): the first one represents the maximum load that the bridge can sustain b (in tonnes); the second one represents the length of the bridge l (in kms); and the third one is the number of vehicles (n) in the convoy.

Each of the next n lines of input contains a pair of positive integers, wi and si (separated by blanks), where wi is the weight of the vehicle (in tonnes) and si is the maximum speed (in kmph) with which this vehicle can travel over the bridge. The weights and speeds of the vehicles are specified in the same order as the order in which the vehicles are queued up. You can assume that 1 <= n,b,l,s <= 1000 and any i in [1..n]: wi <= b.

After the last vehicle, the next test case description begins. The last test case is followed by a line containing three zeros.

Output

The output of the program should be a single real number specifying the minimum time in minutes in which the convoy can cross the bridge. The number should be displayed with one digit after the decimal point.

Sample Input

100 5 10
40 25
50 20
50 20
70 10
12 50
9 70
49 30
38 25
27 50
19 70
0 0 0

Sample Output

75.0

Source

ČVUT FEL++ 2003,Original From Asia 1999


智障DP,不想写题解的,结果好像很久不做题了所以纪念一下

这是今年pku夏令营(不是pkusc)练习赛的F题

难点在读题……

给一个序列,每个点有两个权值w和v。把序列分成若干组,使每组的∑w<=maxn。每个组的权值是k/∑v,要求使所有组权值和最小

你猜我读了多久题?

顺便这题数组只开1000不够

#include<cstdio>
#include<iostream>
#include<cstring>
#include<algorithm>
#include<cmath>
using namespace std;

typedef long long LL;
const int SZ = 100010;
const int INF = 1000000010;

double dp[SZ];
int w[SZ],v[SZ],sum[SZ],st[SZ][30];
int maxn,k,n;

void get_st()
{
    for(int i = 1;i <= n;i ++) st[i][0] = v[i];
    for(int j = 1;j <= log2(n);j ++)
         for(int i = 1;i <= n;i ++)
            st[i][j] = min(st[i][j - 1],st[i + (1 << (j - 1))][j - 1]);
}

int askmin(int l,int r)
{
    int k = log2(r - l + 1);
    return min(st[l][k],st[r - (1 << k) + 1][k]);
}

int main()
{
    while(scanf("%d%d%d",&maxn,&k,&n) && maxn && k && n)
    {
        k *= 60;
        for(int i = 1;i <= n;i ++)
            scanf("%d%d",&w[i],&v[i]),sum[i] = sum[i - 1] + w[i],dp[i] = INF; 
        get_st();
        for(int i = 1;i <= n;i ++)
            for(int j = 0;j < i;j ++)
                if(sum[i] - sum[j] <= maxn)
                    dp[i] = min(dp[i],dp[j] + (double)k / (double)askmin(j + 1,i));
        printf("%.1f\n",dp[n]);
    }
    return 0;
}
  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值