#include <iostream>
#include <vector>
#include <queue>
#include <stack>
#include <algorithm>
using namespace std;
const int SIZE = 100;
/*
第一行输入一个正整数n(1<=n<=5),其代表测试数据数目,即图的数目
第二行输入x(1<=x<=15)代表顶点个数,y(1<=y<=19)代表边的条数
第三行给出图中的顶点集,共x个小写字母表示顶点
接下来每行给出一条边的始点和终点及其权值,用空格相隔,每行代表一条边。
*/
int n, x, y;
struct Edge {
int v;
int w;
Edge(int v, int w) : v(v), w(w) {}
};
vector<Edge> adj[SIZE];
int ve[SIZE], vl[SIZE], in[SIZE];
char c[SIZE];
stack<int> st;
queue<int> qu;
bool topologicalSort() {
queue<int> q;
int num = 0;
for (int i = 0; i < x; i ++) {
if (in[c[i] - 'a'] == 0) {
q.push(c[i] - 'a');
}
}
while (!q.empty()) {
int u = q.front(); q.pop();
qu.push(u);
st.push(u);
num ++;
for (int i = 0; i < adj[u].size(); i ++) {
int v = adj[u][i].v;
int w = adj[u][i].w;
in[v] --;
if (in[v] == 0) q.push(v);
if (ve[u] + w > ve[v]) ve[v] = ve[u] + w;
}
}
if (num == x) return true;
else return false;
}
int CriticalPath() {
fill(ve, ve + SIZE, 0);
if (topologicalSort() == false) {
return -1;
}
int maxVe = -1;
for (int i = 0; i < SIZE; i ++) {
if (ve[i] > maxVe) maxVe = ve[i];
}
fill(vl, vl + SIZE, maxVe);
while (!st.empty()) {
int u = st.top(); st.pop();
for (int i = 0; i < adj[u].size(); i ++) {
int v = adj[u][i].v;
int w = adj[u][i].w;
if (vl[v] - w < vl[u]) {
vl[u] = vl[v] - w;
}
}
}
while (!qu.empty()) {
int u = qu.front(); qu.pop();
for (int j = 0; j < adj[u].size(); j ++) {
int v = adj[u][j].v;
int w = adj[u][j].w;
int e = ve[u]; int l = vl[v] - w;
if (e == l) {
printf("(%c,%c) ", u + 'a', v + 'a');
}
}
}
return maxVe;
}
int main() {
scanf("%d", &n);
while (n --) {
for (int i = 0; i < SIZE; i ++) {
adj[i].clear();
}
fill(in, in + SIZE, 0);
scanf("%d %d", &x, &y);
getchar();
for (int i = 0; i < x; i ++) scanf("%c", &c[i]);
getchar();
char c1, c2;
int w;
for (int i = 0; i < y; i ++) {
scanf("%c %c %d", &c1, &c2, &w);
getchar();
Edge e(c2 - 'a', w);
adj[c1 - 'a'].push_back(e);
in[c2 - 'a'] ++;
}
printf("%d\n", CriticalPath());
}
cin >> n;
return 0;
}
codeup 关键路径 模板
最新推荐文章于 2023-05-02 23:07:24 发布