源代码: #include<cstdio> #include<cstring> #include<queue> using namespace std; struct Node { int S,To,Next; }Edge[20001]; deque <int> Q; int n,m1,m2,Num,i[1001],Sum[1001],Head[1001]; bool In[1001]={0}; void Add(int t1,int t2,int t) //边表。 { Edge[++Num].S=t; Edge[Num].To=t2; Edge[Num].Next=Head[t1]; Head[t1]=Num; } bool SPFA() //SPFA+SLF。 { i[1]=0; In[1]=true; Q.push_back(1); while (!Q.empty()) { int t=Q.front(); In[t]=false; Q.pop_front(); for (int a=Head[t];a;a=Edge[a].Next) { int T=Edge[a].To; if (i[T]>i[t]+Edge[a].S) { Sum[T]=Sum[t]+1; if (Sum[T]>n) return true; i[T]=i[t]+Edge[a].S; if (!In[T]) { In[T]=true; if (!Q.empty()&&i[T]>i[Q.front()]) Q.push_front(T); else Q.push_back(T); } } } } return false; } void Solve() //差分约束系统。 { Num=0; memset(i,0x3f,sizeof(i)); memset(Sum,0,sizeof(Sum)); memset(Head,0,sizeof(Head)); //注意初始化。 for (int a=0;a<m1;a++) { int t,t1,t2; scanf("%d%d%d",&t1,&t2,&t); Add(min(t1,t2),max(t1,t2),t); //编号性质。 } for (int a=0;a<m2;a++) { int t,t1,t2; scanf("%d%d%d",&t1,&t2,&t); Add(max(t1,t2),min(t1,t2),-t); //变号。 } if (SPFA()) //存在负环 printf("-1 "); else if (i[n]==i[0]) printf("-2 "); else printf("%d ",i[n]); } int main() { while (scanf("%d%d%d",&n,&m1,&m2)==3) //坑人的多组数据! Solve(); return 0; } /* 因为是队列,所以编号是单调递增的,只需要区分符号,再SPFA即可。 */