最后问满足所有不等式的序列是否存在,若满足输出lamentable kingdom,不满足输出successful conspiracy。
需要注意1、用spfa判断负环的时候要加入一个新节点,其与所有节点连边,权值为0。此题中新节点不能够用节点0,因为0节点在之前建图中可能已经用到(a和b虽然从1开始,但是建图时有插入a-1的可能)。所以新节点要用n+1号。2、spfa判断负环是在num数组值加一之后,不是放在队列为空之后统一判断,因为如果有负环队列可能根本就出不来。
#include <stdio.h> #include <string.h> #define INF 0x3fffffff #define N 115 struct edge{ int y,next,w; }e[1000]; int n,m; char op[5]; int num[N],first[N],dis[N],top,q[100000]; void add(int x,int y,int w){ e[top].y = y; e[top].w = w; e[top].next = first[x]; first[x] = top++; } int relax(int x,int y,int w){ if(dis[x] + w < dis[y]){ dis[y] = dis[x] + w; return 1; } return 0; } int spfa(){ int i,now,used[N],front,rear; memset(used,0,sizeof(used)); memset(num,0,sizeof(num)); used[n+1] = 1; dis[n+1] = 0; for(i = 0;i<=n;i++) dis[i] = INF; front = rear = -1; q[++rear] = n+1; while(front < rear){ now = q[++front]; used[now] = 0; for(i = first[now];i!=-1;i=e[i].next) if(relax(now,e[i].y,e[i].w) && !used[e[i].y]){ q[++rear] = e[i].y; used[e[i].y] = 1; num [e[i].y]++; if(num[e[i].y] > n) return 0; } } return 1; } int main(){ freopen("a.txt","r",stdin); while(scanf("%d",&n) && n){ int i,a,b,c; top=0; memset(first,-1,sizeof(first)); scanf("%d",&m); for(i = 0;i<m;i++){ scanf("%d %d %s %d",&a,&b,op,&c); if(!strcmp(op,"gt")) add(a+b,a-1,-c-1); else add(a-1,a+b,c-1); } for(i = 1;i<=n;i++) add(n+1,i,0); if(spfa()) printf("lamentable kingdom\n"); else printf("successful conspiracy\n"); } return 0; }