您的位置:首页 > 其它

poj 3114 Countries in War

2014-02-18 08:22 363 查看
http://poj.org/problem?id=3114

这道题和poj 3592 一样,先缩点再spfa求最短路

#include <cstdio>
#include <cstring>
#include <queue>
#include <algorithm>
#define maxn 300000
using namespace std;

const int inf=1<<30;
int head[maxn],head1[maxn],dfn[maxn],low[maxn],belong[maxn],stack1[maxn],dis[maxn],cnt[maxn];
int e,ee,bcc_clock,bcnt,top,N,E,x,y,h,k,o,d;
bool vis[maxn],visi[maxn];

struct node
{
int u,v,w,next;
}p[maxn];

struct node1
{
int u,v,w,next;
}pp[maxn];

void add(int u,int v,int w)
{
p[e].u=u;
p[e].v=v;
p[e].w=w;
p[e].next=head[u];
head[u]=e++;
}

void addnode(int u,int v,int w)
{
pp[ee].u=u;pp[ee].v=v;
pp[ee].w=w;
pp[ee].next=head1[u];
head1[u]=ee++;
}

void tarjan(int u)
{
vis[u]=true;
dfn[u]=low[u]=++bcc_clock;
stack1[++top]=u;
for(int i=head[u]; i!=-1; i=p[i].next)
{
int v=p[i].v;
if(!dfn[v])
{
tarjan(v);
low[u]=min(low[u],low[v]);
}
else if(vis[v])
{
low[u]=min(low[u],dfn[v]);
}
}
if(dfn[u]==low[u])
{
bcnt++;
int j;
do
{
j=stack1[top--];
vis[j]=false;
belong[j]=bcnt;
}while(j!=u);
}
}

void deal()
{
bcc_clock=0,bcnt=0,top=0;
memset(vis,false,sizeof(vis));
memset(belong,0,sizeof(belong));
memset(dfn,0,sizeof(dfn));
for(int i=1; i<=N; i++)
{
if(!dfn[i])
{
tarjan(i);
}
}
}

void inti()
{
memset(head,-1,sizeof(head));
memset(head1,-1,sizeof(head1));
e=0,ee=0;
}
bool ralex(int u,int v,int w)
{
if(dis[v]>dis[u]+w)
{
dis[v]=dis[u]+w;
return true;
}
return false;
}

bool spfa(int src)
{
memset(visi,false,sizeof(visi));
memset(cnt,0,sizeof(cnt));
queue<int>q;
for(int i=0; i<=N; i++)
{
dis[i]=inf;
}
dis[src]=0;
visi[src]=true;
q.push(src);
while(!q.empty())
{
int u=q.front();q.pop();
visi[u]=false;
for(int i=head1[u]; i!=-1; i=pp[i].next)
{
if(ralex(u,pp[i].v,pp[i].w)&&!visi[pp[i].v])
{
if((++cnt[pp[i].v])>N) return false;
visi[pp[i].v]=true;
q.push(pp[i].v);
}
}
}
return true;
}

int main()
{
while(scanf("%d%d",&N,&E)!=EOF)
{
inti();
if(N==0&&E==0) break;
for(int i=0; i<E; i++)
{
scanf("%d%d%d",&x,&y,&h);
add(x,y,h);
}
deal();
for(int i=1; i<=N; i++)
{
for(int j=head[i]; j!=-1; j=p[j].next)
{
int v=p[j].v;
if(belong[i]==belong[v]) addnode(i,v,0);
else if(belong[i]!=belong[v]) addnode(i,v,p[j].w);
}
}
scanf("%d",&k);
for(int i=0; i<k; i++)
{
scanf("%d%d",&o,&d);
spfa(o);
if(dis[d]!=inf)
printf("%d\n",dis[d]);
else
printf("Nao e possivel entregar a carta\n");
}
printf("\n");
}
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: