BZOJ1880: [Sdoi2009]Elaxia的路线

来源:互联网 发布:python怎么取最大 编辑:程序博客网 时间:2024/05/01 09:55

康复训练的第一题智障了一个下午


x1,y1,x2,y2
4个点每个点都跑一次SPFA,计算出这4个点到所有点的最短距离
然后对x1到y1的所有最短路径建一个拓扑图,先按照第二个人从x2到y2走,沿x1到y1建的拓扑图做DP,如果当前边既在x1到y1的最短路上又在x2到y2的最短路上,就可以转移,因为是路径的交集不分方向,所以再按照第二个人从y2到x2走,沿x1到y1建的拓扑图做DP,如果如果当前边既在x1到y1的最短路上又在y2到x2的最短路上,就可以转移


code:

#include<set>#include<map>#include<deque>#include<queue>#include<stack>#include<ctime>#include<bitset>#include<string>#include<vector>#include<cstdio>#include<cstdlib>#include<cstring>#include<climits>#include<complex>#include<iostream>#include<algorithm>#define ll long longusing namespace std;const int maxn = 3000;const int maxm = 2510000;void read(int &x){    char c; int f=1;    while(!((c=getchar())>='0'&&c<='9'));    x=c-'0';    while((c=getchar())>='0'&&c<='9') x=(x<<3)+(x<<1)+c-'0';}struct edge{    int y,c,nex;    edge(){}    edge(int _y,int _c,int _nex){y=_y;c=_c;nex=_nex;}}a[maxm]; int len,fir[maxn];int n,m,x1,x2,t1,t2;int d[4][maxn];void ins(int x,int y,int c){    len++;    a[len].y=y; a[len].c=c; a[len].nex=fir[x]; fir[x]=len;    len++;    a[len].y=x; a[len].c=c; a[len].nex=fir[y]; fir[y]=len;}queue<int>q;bool v[maxn];void search(int st,int l){    memset(d[l],63,sizeof d[l]);    d[l][st]=0; q.push(st);    while(!q.empty())    {        int x=q.front(); q.pop(); v[x]=false;        for(int k=fir[x];k;k=a[k].nex)        {            int y=a[k].y;            if(d[l][y]>d[l][x]+a[k].c)            {                d[l][y]=d[l][x]+a[k].c;                if(!v[y]) q.push(y),v[y]=true;            }        }    }}int f[maxn];int _in[maxn],cyin[maxn];void up(int &x,int y){if(y>x)x=y;}int main(){    memset(fir,0,sizeof fir); len=0;    read(n); read(m);    read(x1); read(t1); read(x2); read(t2);    for(int i=1;i<=m;i++)    {        int x,y,c; read(x); read(y); read(c);        ins(x,y,c);    }    search(x1,0); search(t1,1); search(x2,2); search(t2,3);    int de=d[0][t1];    q.push(x1);    while(!q.empty())    {        int x=q.front(); q.pop();        for(int k=fir[x];k;k=a[k].nex)        {            int y=a[k].y,c=a[k].c;            if(d[0][x]+c+d[1][y]==de)            {                if(!v[y]) q.push(y),v[y]=true;                _in[y]++;            }        }    }    int ans=0;    for(int i=1;i<=n;i++) cyin[i]=_in[i];    memset(f,0,sizeof f);    q.push(x1);    while(!q.empty())    {        int x=q.front(); q.pop();        for(int k=fir[x];k;k=a[k].nex)        {            int y=a[k].y,c=a[k].c;            if(d[0][x]+c+d[1][y]==de)            {                cyin[y]--;                if(!cyin[y]) q.push(y);                 if(d[2][x]+c+d[3][y]==d[2][t2])                {                    up(f[y],f[x]+c);                    up(ans,f[y]);                }            }        }    }    memset(f,0,sizeof f);    for(int i=1;i<=n;i++) cyin[i]=_in[i];    q.push(x1);    while(!q.empty())    {        int x=q.front(); q.pop(); v[x]=false;        for(int k=fir[x];k;k=a[k].nex)        {            int y=a[k].y,c=a[k].c;            if(d[0][x]+c+d[1][y]==de)            {                cyin[y]--;                if(!cyin[y]) q.push(y);                 if(d[3][x]+c+d[2][y]==d[2][t2])                {                    up(f[y],f[x]+c);                    up(ans,f[y]);                }            }        }    }    printf("%d\n",ans);    return 0;}
0 0
原创粉丝点击