AmazingCounters.com

BZOJ 2763: [JLOI2011]飞行路线 【SPFA】

Alice和Bob现在要乘飞机旅行,他们选择了一家相对便宜的航空公司。该航空公司一共在n个城市设有业务,设这些城市分别标记为0到n-1,一共有m种航线,每种航线连接两个城市,并且航线有一定的价格。Alice和Bob现在要从一个城市沿着航线到达另一个城市,途中可以进行转机。航空公司对他们这次旅行也推出优惠,他们可以免费在最多k种航线上搭乘飞机。那么Alice和Bob这次出行最少花费多少?Input数据的第一行有三个整数,n,m,k,分别表示城市数,航线数和免费乘坐次数。第二行有两个整数,s,t,分别表示他们出行的起点城市编号和终点城市编号。(0<=s,t<n)接下来有m行,每行三个整数,a,b,c,表示存在一种航线,能从城市a到达城市b,或从城市b到达城市a,价格为c。(0<=a,b<n,a与b不相等,0<=c<=1000) Output 只有一行,包含一个整数,为最少花费。Sample Input5 6 1
0 4
0 1 5
1 2 5
2 3 5
3 4 5
2 3 3
0 2 100
Sample Output8HINT

 

对于30%的数据,2<=n<=50,1<=m<=300,k=0;

 

对于50%的数据,2<=n<=600,1<=m<=6000,0<=k<=1;

 

对于100%的数据,2<=n<=10000,1<=m<=50000,0<=k<=10.

 

BZOJ2662的姊妹题TUT 直接敲

 

#include <stdio.h>

#include <iostream>

#include<queue>

#include <string.h>

#include <algorithm>

#define maxn 10001

#define maxm 100001

#define esp 0.00000001

using namespace std;

typedef pair<int,int> pii;

int head[maxn],point[maxm],next[maxm],value[maxm],now=0;

int n,m,kk,s,t,dist[maxn][11];

void add(int x,int y,int v)

{

    next[++now]=head[x];

    head[x]=now;

    point[now]=y;

    value[now]=v;

}

int spfa(int s)

{

    memset(dist,0x3f,sizeof(dist));

    for(int i=0;i<=kk;i++)dist[s][i]=0;

    int visit[maxn][11]={{0}};

    visit[s][0]=1;

    queue<pii>q;

    q.push(make_pair(s,0));

    while(!q.empty())

    {

        pii uu=q.front();

        q.pop();

        int u=uu.first,b=uu.second;

        visit[u][b]=0;

        for(int i=head[u];i;i=next[i])

        {

            int k=point[i];

            if(dist[u][b]+value[i]<dist[k][b])

            {

                dist[k][b]=dist[u][b]+value[i];

                if(visit[k][b]==0)

                {

                    visit[k][b]=1;

                    q.push(make_pair(k,b));

                }

            }

            if(dist[u][b]<dist[k][b+1])

            if(b+1<=kk)

            {

                dist[k][b+1]=dist[u][b];

                if(visit[k][b+1]==0)

                {

                    visit[k][b+1]=1;

                    q.push(make_pair(k,b+1));

                }

            }

        }

    }

    int ans=0x3f3f3f3f;

    for(int i=0;i<=kk;i++)

    {

        if(dist[t][i]==-1)continue;

        ans=min(ans,dist[t][i]);

    }

    return ans;

}

int main()

{

    int x,y,v;

    scanf("%d%d%d%d%d",&n,&m,&kk,&s,&t);

    for(int i=1;i<=m;i++)

    {

        scanf("%d%d%d",&x,&y,&v);

        add(x,y,v);

        add(y,x,v);

    }

    printf("%d\n",spfa(s));

    return 0;

}

posted @ 2014-10-30 18:15  philippica  阅读(216)  评论(0编辑  收藏  举报