bellford man判正环
共能连n-1条边,松弛n-1次后
若能继续松弛就是有正环
#include <iostream>
#include <stdio.h>
#include <algorithm>
#include <queue>
#include <cstring>
#include <math.h>
#include <map>
#define FOR(i,j,k) for(int i=j;i<=k;i++)
using namespace std;
int n,m;
int s; //持有第s种
double v; //持有s的本金
int tot;
double d[110];//s到各点
struct node{
int a;
int b;
double r; //rate
double c; //手续费
}nd[220];
bool bellman()
{
memset(d,0,sizeof(d));
d[s]=v;
bool flag;
for(int i=1;i<=n-1;i++){
flag=false;
for(int j=1;j<=tot;j++){
if(d[nd[j].b]<(d[nd[j].a]-nd[j].c)*nd[j].r)
{
d[nd[j].b]=(d[nd[j].a]-nd[j].c)*nd[j].r;
flag=true;
}
}
if(!flag)
break;
}
for(int i=1;i<=tot;i++)
if(d[nd[i].b]<(d[nd[i].a]-nd[i].c)*nd[i].r)
return true;
return false;
}
int main()
{
while(scanf("%d%d%d%lf",&n,&m,&s,&v)!=EOF)
{
tot=0;
int a,b;
double rab,cab,rba,cba;
while(m--)
{
scanf("%d%d%lf%lf%lf%lf",&a,&b,&rab,&cab,&rba,&cba);
tot++;
nd[tot].a=a;
nd[tot].b=b;
nd[tot].r=rab;
nd[tot].c=cab;
tot++;
nd[tot].a=b;
nd[tot].b=a;
nd[tot].r=rba;
nd[tot].c=cba;
}
//cout<<tot<<endl;
if(bellman())
cout<<"YES"<<endl;
else cout<<"NO"<<endl;
}
return 0;
}