poj-openjudge 1037:City Metro 解题报告

题目

2013北大校赛总结

题意:

某城公交有n个车站,每天发m趟车(单向),行走时间及顺序均固定。

有p个乘客,告诉你他们到达某个车站等车的时间,需要你安排m趟车,使得他们都能上车,并且总的等待时间最短。

解法:

将所有乘客的之间转换成假如一道车站就上车那么到终点站的时间。然后对这个时间数组进行排序,然后我们就要将数组分成m个区间,每个区间表示区间里的乘客乘同一辆车。

剩下的就简单了,一个二维dp[i][j],表示第i个乘客是第j趟车的最后一个乘客,用前缀和可以很快的转移。

注意车可能在负的时间开出。

Time:0ms
Memory:252kB	
Length:1188 B

#include <iostream>
#include <cstdio>
#include <queue>
#include <cmath>
#include <cstring>
#include <algorithm>
#define EPS 1e-3
#define MAXN 210
#define INF 1000000009
using namespace std;
int sum[MAXN],per[MAXN];
int len[MAXN];
int dp[110][100];
int main()
{
    //freopen("C:\\Documents and Settings\\k99\\My Documents\\input.txt","r",stdin);
    int t,n,m,p,s;
    scanf("%d",&t);
    while(t--)
    {
        scanf("%d%d%d",&n,&m,&p);
        for(int i=0;i<n-1;++i)
            scanf("%d",&len[i]);
        for(int i=n-2;i>=0;--i)
            len[i]+=len[i+1];
        for(int i=1;i<=p;++i)
            scanf("%d%d",&s,&per[i]),per[i]+=len[s-1];
        for(int i=0;i<=p;++i)
            for(int j=0;j<=m;++j)
                dp[i][j]=INF;
        sort(per+1,per+p+1);
        sum[0]=0;
        for(int i =1;i<=p;++i)
            sum[i]=sum[i-1]+per[i];
        dp[0][0]=0;
        for(int i=1;i<=p;++i)
            for(int j=1;j<=m;++j)
                for(int ii=0;ii<i;++ii)
                    dp[i][j]=min((long long)dp[i][j],dp[ii][j-1]+(long long)(i-ii)*per[i]-sum[i]+sum[ii]);
        printf("%d\n",dp[p][m]);
    }
    return 0;
}


你可能感兴趣的:(poj-openjudge 1037:City Metro 解题报告)