zoukankan      html  css  js  c++  java
  • [bzoj2324][ZJOI2011]营救皮卡丘

    来自FallDream的博客,未经允许,请勿转载,谢谢。


    皮卡丘被火箭队用邪恶的计谋抢走了!这三个坏家伙还给小智留下了赤果果的挑衅!为了皮卡丘,也为了正义,小智和他的朋友们义不容辞的踏上了营救皮卡丘的道路。

    火箭队一共有N个据点,据点之间存在M条双向道路。据点分别从1到N标号。小智一行K人从真新镇出发,营救被困在N号据点的皮卡丘。为了方便起见,我们将真新镇视为0号据点,一开始K个人都在0号点。

    由于火箭队的重重布防,要想摧毁K号据点,必须按照顺序先摧毁1到K-1号据点,并且,如果K-1号据点没有被摧毁,由于防御的连锁性,小智一行任何一个人进入据点K,都会被发现,并产生严重后果。因此,在K-1号据点被摧毁之前,任何人是不能够经过K号据点的。

    为了简化问题,我们忽略战斗环节,小智一行任何一个人经过K号据点即认为K号据点被摧毁。被摧毁的据点依然是可以被经过的。

    K个人是可以分头行动的,只要有任何一个人在K-1号据点被摧毁之后,经过K号据点,K号据点就被摧毁了。显然的,只要N号据点被摧毁,皮卡丘就得救了。

    野外的道路是不安全的,因此小智一行希望在摧毁N号据点救出皮卡丘的同时,使得K个人所经过的道路的长度总和最少。

    请你帮助小智设计一个最佳的营救方案吧! n<=150 k<=10

    首先这个数据范围显然是费用流qaq

    然后自己yy了一个建图,把原图拆点,强制他们之间的边流1,然后从S向0连k的边,向每个点的出点连1的边,直接把原图的边扔进去了,轻松wa题,想了想貌似没法保证它们走的顺序....

    所以考虑把两点之间可行的最短路径直接求出来,然后建边,就能保证结果合法了。也就是对于i->j的路径,强制只走小等于j的点,floyd求出之后从i的出点向j的入点连费用是dis[i][j]的边就行了。

    嗯这个强制流1其实就是从一个点的入点向T连流量为1的边,从S向出点连流量为1的边,满足最大流的时候一定满流。如果还不是很清楚可以学习一下带上下界网络流的一套理论。

    #include<iostream>
    #include<cstdio>
    #include<cstring>
    #include<queue>
    #define ll long long
    #define S 0
    #define T 303
    #define INF 1000000000
    using namespace std;
    inline ll read()
    {
        ll x = 0 , f = 1; char ch = getchar();
        while(ch < '0' || ch > '9'){ if(ch == '-') f = -1;  ch = getchar();}
        while(ch >= '0' && ch <= '9'){x = x * 10 + ch - '0';ch = getchar();}
        return x * f;
    }
    
    int n,m,k,cnt=1,head[T+5],ans=0,pi=0,d[T+5],dis[155][155];
    bool mark[T+5],inq[T+5];
    deque<int> q;
    struct edge{int to,next,w,c;}e[80005];
    
    inline void ins(int f,int t,int w,int c)
    {
        e[++cnt]=(edge){t,head[f],w,c}; head[f]=cnt;
        e[++cnt]=(edge){f,head[t],0,-c};head[t]=cnt;
    } 
    
    bool modlabel()
    {
        q.push_back(T);
        for(int i=S;i<T;i++)d[i]=INF;d[T]=0;inq[T]=1;
        while(!q.empty())
        {
            int x=q.front();q.pop_front();
            for(int i=head[x];i;i=e[i].next)
                if(e[i^1].w&&d[x]+e[i^1].c<d[e[i].to])
                {
                    d[e[i].to]=d[x]+e[i^1].c;
                    if(!inq[e[i].to])
                    {
                        inq[e[i].to]=1;
                        if(d[e[i].to]<d[q.size()?q.front():0]) q.push_front(e[i].to);
                        else q.push_back(e[i].to);
                    }
                }
            inq[x]=0;
        }
        for(int i=S;i<=T;i++)    
            for(int j=head[i];j;j=e[j].next)
                e[j].c+=d[e[j].to]-d[i];
        return pi+=d[S],d[S]<INF;
    }
    
    int dfs(int x,int f)
    {
        if(x==T) return ans+=pi*f,f;
        int used=0;mark[x]=1;
        for(int i=head[x];i;i=e[i].next)
            if(e[i].w&&!e[i].c&&!mark[e[i].to])
            {
                int w=dfs(e[i].to,min(f-used,e[i].w));
                used+=w;e[i].w-=w;e[i^1].w+=w;
                if(f==used) return f; 
            }
        return used;
    }
    
    int main()
    {
        n=read()+1;m=read();k=read();
        for(int i=1;i<=n;i++)
            for(int j=1;j<=n;j++)
                if(i!=j) dis[i][j]=INF;
        ins(S,1,k,0);
        for(int i=2;i<=n;i++) ins(i+n,T,1,0),ins(S,i,1,0);
        for(int i=1;i<=m;i++)
        {
            int x=read()+1,y=read()+1,c=read();
            dis[x][y]=min(dis[x][y],c);
            dis[y][x]=min(dis[y][x],c);
        }
        for(int k=1;k<=n;k++)
            for(int i=1;i<=n;i++)
                for(int j=1;j<=n;j++)
                    if(dis[i][k]+dis[k][j]<dis[i][j]&&max(i,j)>=k)
                        dis[i][j]=dis[i][k]+dis[k][j];
        for(int i=1;i<=n;i++)
            for(int j=i+1;j<=n;j++)
                if(dis[i][j]<INF) ins(i,j+n,INF,dis[i][j]);
        while(modlabel())
            do memset(mark,0,sizeof(mark));
            while(dfs(S,INF));
        printf("%d
    ",ans);
        return 0;
    }
  • 相关阅读:
    修复 Visual Studio Error “No exports were found that match the constraint”
    RabbitMQ Config
    Entity Framework Extended Library
    Navisworks API 简单二次开发 (自定义工具条)
    NavisWorks Api 简单使用与Gantt
    SQL SERVER 竖表变成横表
    SQL SERVER 多数据导入
    Devexpress GridControl.Export
    mongo DB for C#
    Devexress XPO xpPageSelector 使用
  • 原文地址:https://www.cnblogs.com/FallDream/p/bzoj2324.html
Copyright © 2011-2022 走看看