BZOJ1715: [Usaco2006 Dec]Wormholes 虫洞
1715: [Usaco2006 Dec]Wormholes 虫洞
Time Limit: 5 Sec Memory Limit: 64 MBSubmit: 475 Solved: 263
[Submit][Status]
Description
John 在他的农场中闲逛时发现了许多虫洞。虫洞可以看作一条十分奇特的有向边,并可以使你返回到过去的一个时刻(相对你进入虫洞之前)。John的每个农场有M 条小路(无向边)连接着N (从1..N标号)块地,并有W个虫洞。其中1<=N<=500,1<=M<=2500,1<=W<=200。 现在John想借助这些虫洞来回到过去(出发时刻之前),请你告诉他能办到吗。 John将向你提供F(1<=F<=5)个农场的地图。没有小路会耗费你超过10000秒的时间,当然也没有虫洞回帮你回到超过10000秒 以前。
Input
* Line 1: 一个整数 F, 表示农场个数。
* Line 1 of each farm: 三个整数 N, M, W。
* Lines 2..M+1 of each farm: 三个数(S, E, T)。表示在标号为S的地与标号为E的地中间有一条用时T秒的小路。
* Lines M+2..M+W+1 of each farm: 三个数(S, E, T)。表示在标号为S的地与标号为E的地中间有一条可以使John到达T秒前的虫洞。
Output
* Lines 1..F: 如果John能在这个农场实现他的目标,输出"YES",否则输出"NO"。
Sample Input
2
3 3 1
1 2 2
1 3 4
2 3 1
3 1 3
3 2 1
1 2 3
2 3 4
3 1 8
3 3 1
1 2 2
1 3 4
2 3 1
3 1 3
3 2 1
1 2 3
2 3 4
3 1 8
Sample Output
NO
YES
YES
HINT
Source
题解:
裸的spfa判负环,用dfs,复习了一下。。。
代码:
1 #include<cstdio> 2 3 #include<cstdlib> 4 5 #include<cmath> 6 7 #include<cstring> 8 9 #include<algorithm> 10 11 #include<iostream> 12 13 #include<vector> 14 15 #include<map> 16 17 #include<set> 18 19 #include<queue> 20 21 #include<string> 22 23 #define inf 1000000000 24 25 #define maxn 100000 26 27 #define maxm 100000 28 29 #define eps 1e-10 30 31 #define ll long long 32 33 #define pa pair<int,int> 34 35 #define for0(i,n) for(int i=0;i<=(n);i++) 36 37 #define for1(i,n) for(int i=1;i<=(n);i++) 38 39 #define for2(i,x,y) for(int i=(x);i<=(y);i++) 40 41 #define for3(i,x,y) for(int i=(x);i>=(y);i--) 42 43 #define mod 1000000007 44 45 using namespace std; 46 47 inline int read() 48 49 { 50 51 int x=0,f=1;char ch=getchar(); 52 53 while(ch<'0'||ch>'9'){if(ch=='-')f=-1;ch=getchar();} 54 55 while(ch>='0'&&ch<='9'){x=10*x+ch-'0';ch=getchar();} 56 57 return x*f; 58 59 } 60 struct edgs{int go,next;double w,w0;}e[maxm]; 61 double d[maxn]; 62 int n,m,k,tot,v[maxn],head[maxn]; 63 bool mark[maxn],flag; 64 void insert(int x,int y,int z) 65 { 66 e[++tot].go=y;e[tot].next=head[x];head[x]=tot;e[tot].w=z; 67 } 68 void spfa(int x) 69 { 70 if(mark[x]){flag=1;return;} 71 mark[x]=1; 72 for(int i=head[x],y;i;i=e[i].next) 73 if(d[x]+e[i].w<d[y=e[i].go]) 74 { 75 d[y]=d[x]+e[i].w; 76 spfa(y); 77 if(flag)break; 78 } 79 mark[x]=0; 80 } 81 82 int main() 83 84 { 85 86 freopen("input.txt","r",stdin); 87 88 freopen("output.txt","w",stdout); 89 90 int cs=read(); 91 while(cs--) 92 { 93 memset(head,0,sizeof(head));tot=0; 94 n=read();m=read();k=read(); 95 for1(i,m){int x=read(),y=read(),z=read();insert(x,y,z);insert(y,x,z);} 96 for1(i,k){int x=read(),y=read(),z=read();insert(x,y,-z);} 97 for1(i,n)d[i]=mark[i]=0; 98 flag=0; 99 for1(i,n) 100 { 101 spfa(i); 102 if(flag)break; 103 } 104 if(flag)printf("YES\n");else printf("NO\n"); 105 } 106 107 return 0; 108 109 }