洛谷P1938 [USACO09NOV]Job Hunt S

(large{题目链接})
(\)
(Large extbf{Solution: } large{对于题目中的飞机与道路,可以当作边权为负与零的一条边。\由于每到一个城市能获得D的收益,那么可以给每条边的边权再加一个D,最后Spfa跑最长路顺便判环即可。})
(\)
(Large extbf{Code: })

#include <bits/stdc++.h>
#define gc() getchar() 
#define LL long long
#define rep(i, a, b) for (int i = (a); i <= (b); ++i)
#define _rep(i, a, b) for (int i = (a); i >= (b); --i)
using namespace std;
const int N = 225;
const int inf = 0x7fffffff;
int n, m1, m2, s, cnt, val, ans, head[N], vis[N], r[N], c[N];

struct Edge {
	int to, next, val;
}e[N << 1];

inline int read() {
	int x = 0;
	char ch = gc();
	while (!isdigit(ch)) ch = gc();
	while (isdigit(ch)) x = x * 10 + ch - '0', ch = gc();
	return x; 
}

inline void add(int x, int y, int w) {
	e[++cnt].to = y;
	e[cnt].next = head[x];
	e[cnt].val = w;
	head[x] = cnt;
}

inline bool Spfa() {
	queue<int> q;
	rep(i, 1, n) c[i] = -inf;
	c[s] = ans = val, r[1] = 0; q.push(1);
	while (!q.empty()) {
		int x = q.front(); q.pop();
		vis[x] = 0;
		for (int i = head[x]; i ; i = e[i].next) {
			int u = e[i].to;
			if (c[u] < c[x] + e[i].val) {
				c[u] = c[x] + e[i].val;
				ans = max(ans, c[u]);
				if (!vis[u]) vis[u] = 1, q.push(u);
				if (++r[u] > n) return false;
			}
		}
	}
	return true;
}

int main() {
	val = read(), m1 = read(), n = read(), m2 = read(), s = read();
	int x, y, w;
	while (m1--) x = read(), y = read(), add(x, y, val);
	while (m2--) x = read(), y = read(), w = read(), add(x, y, val - w);
	int flg = Spfa();
	if (flg) cout << ans << endl;
	else cout << "-1" << endl;
	return 0;
} 
原文地址:https://www.cnblogs.com/Miraclys/p/12578085.html