POJ-3259-Wormholes

来源:互联网 发布:盘锦企业数据 编辑:程序博客网 时间:2024/06/10 20:34
题目大意:利用虫洞的时光旅行,若能回到过去,则输出"YES",否则"NO"。
给定F(1<=F<=5)组数据,对应与一个farm,每组数据对应一个结果。
对于其中一组数据,给定 N , M , W ,N为点数,M为无向边数(普通路径,通过之后时间前进),W为有向边数(虫洞,通过虫洞之后时间倒退),求每组数据是否存在一条回路能使时间倒退。
解题思路:若存在这样一条回路,则图中肯定存在负环。只要判断是否有负环就行了。
AC Code (1): bellmanFord   Memory: 236K      Time: 141Ms
#include <iostream> 
#include <cstdio> 
#include <cstring> 
#define Inf 0x7fffffff 
#define MaxV 501 
#define MaxE 6000 
using namespace std; 
int F,N,M,W; 
struct Edge{    int to,next,time;}edge[MaxE]; 
int size,head[MaxE]; 
void InsertEdge(int from,int to,int time) 
{      edge[size].to=to;    edge[size].time=time; 
   edge[size].next=head[from];    head[from]=size++; 
} 
int dist[MaxV]; 
bool bellmanFord() 
{  bool flag;    int i,j,k,to; 
   memset(dist,Inf,sizeof(dist)); 
   dist[1]=0; 
   for(i=1;i<=N-1;i++) 
  {  flag=false; 
     for(j=1;j<=N;j++) 
     {  for(k=head[j];k+1;k=edge[k].next) 
          {                to=edge[k].to; 
           if(dist[to]>dist[j]+edge[k].time) 
             {                    flag=true;                    dist[to]=dist[j]+edge[k].time;                } 
          } 
       } 
      if(!flag)        break; 
   } 
   for(j=1;j<=N;j++) 
   {   for(k=head[j];k+1;k=edge[k].next) 
      {            to=edge[k].to;            if(dist[to]>dist[j]+edge[k].time)            return false;        } 
   } 
   return true; 
} 
void init() 
{    int i;    int from,to,time; 
  scanf("%d%d%d",&N,&M,&W); 
  size=0;    memset(head,-1,sizeof(head)); 
  for(i=0;i<M;i++) 
  {  scanf("%d%d%d",&from,&to,&time); 
     InsertEdge(from,to,time);InsertEdge(to,from,time); 
   } 
  for(i=0;i<W;i++) 
   {  scanf("%d%d%d",&from,&to,&time);        InsertEdge(from,to,0-time);    } 
} 
int main() 
{    //freopen("in.txt","r",stdin); 
    scanf("%d",&F); 
    while(F--) 
    {        init(); 
     if(bellmanFord())   printf("NO\n"); 
     else printf("YES\n"); 
    } 
    return 0; 
}

AC Code
 (2):spfa  Memory: 256K  Time: 141Ms
#include <iostream> 
#include <cstdio> 
#include <cstring> 
#include <queue> 
#define Inf 0x7fffffff 
#define MaxV 501 
#define MaxE 6000 
using namespace std; 
int F,N,M,W; 
struct Edge {    int to,next,time;}edge[MaxE]; 
int size,head[MaxE]; 
void InsertEdge(int from,int to,int time) 
{    edge[size].to=to;    edge[size].time=time; 
 edge[size].next=head[from];    head[from]=size++; 
} 
int dist[MaxV];int cot[MaxV];bool vst[MaxV]; 
bool spfa() 
{    queue<int> que;    int i,from,to; 
  for(i=0;i<=N;i++)    dist[i]=Inf;    //这里用 memset出错
  memset(vst , 0 ,sizeof( vst)); 
  memset(cot , 0 ,sizeof( cot)); 
  dist[1]=0,vst[1]=1;    que.push(1); 
  while(!que.empty()) 
  {        from=que.front(),vst[from]=0,que.pop();        cot[from]++;      
    if(cot[from]>=N)    return false
    for(i=head[from];i+1;i=edge[i].next) 
    {  to=edge[i].to; 
       if(dist[to]>dist[from]+edge[i].time) 
       {                dist[to]=dist[from]+edge[i].time; 
           if(!vst[to]) 
             que.push(to),vst[to]=1; 
       } 
    } 
  } 
return true; 
}
void init() 
{    int i;    int from,to,time; 
  scanf("%d%d%d",&N,&M,&W); 
  size=0;    memset(head,-1,sizeof(head)); 
  for(i=0;i<M;i++) 
  {  scanf("%d%d%d",&from,&to,&time); 
     InsertEdge(from,to,time);InsertEdge(to,from,time); 
  } 
  for(i=0;i<W;i++) 
  {  scanf("%d%d%d",&from,&to,&time); 
     InsertEdge(from,to,0-time); 
  } 
} 
int main()
{    scanf("%d",&F); 
  while(F--)
  {  init(); 
     if(spfa())   printf("NO\n"); 
     else printf("YES\n"); 
  } 
return 0; 
}
0 0
原创粉丝点击