求条,样例没输出
查看原帖
求条,样例没输出
681755
CuteGirlGC楼主2024/5/26 12:36
#include <algorithm>
#include <iostream>
#include <vector>

using namespace std;

const int kMaxN = 2e5 + 1, kMaxL = 20;

int n, m, sum;
struct Side {
  int u, v, w;
  friend bool operator>(Side a, Side b) {
    return a.w > b.w;
  }
} s[kMaxN];
struct V {
  int d, f[20], st[20];
  vector<pair<int, int>> e;
} v[kMaxN];
class DSU {
 private:
  static const int kMaxN = 2e5 + 1;
  int n;
  vector<int> f;

 public:
  DSU() {}
  DSU(int size) {
    n = size;
    f.clear();
    for (int i = 0; i <= n; i++) {
      f.push_back(i);
    }
  }
  int Find(int x) {
    return f[x] == x ? x : f[x] = Find(f[x]);
  }
  bool Union(int x, int y) {
    int fx = Find(x), fy = Find(y);
    if (fx == fy) {
      return 0;
    } else {
      f[f[y]] = f[x];
      return 1;
    }
  }
  bool Same(int x, int y) {
    return Find(x) == Find(y);
  }
};

void Kruskal(DSU dsu) {
  sort(s + 1, s + m + 1, greater<Side>());
  for (int i = 1; i <= m; i++) {
    if (dsu.Union(s[i].u, s[i].v)) {
      sum += s[i].w;
      v[s[i].u].e.push_back({s[i].v, s[i].w});
      v[s[i].v].e.push_back({s[i].u, s[i].w});
    }
  }
}

void Walk(int x, int f) {
  v[x].f[0] = f, v[x].d = v[f].d + 1;
  for (pair<int, int> i : v[x].e) {
    if (i.first != f) {
      v[i.first].st[0] = i.second;
      Walk(i.first, x);
    }
  }
}

void CalcF() {
  for (int j = 0; j < kMaxL - 1; j++) {
    for (int i = 1; i <= n; i++) {
      v[i].f[j + 1] = v[v[i].f[j]].f[j];
      v[i].st[j + 1] = min(v[i].st[j], v[v[i].f[j]].st[j]);
    }
  }
}

int Query(int x, int y) {
  int ans = 1e9;
  if (v[x].d > v[y].d) {
    swap(x, y);
  }
  for (int i = 0; i < kMaxL; i++) {
    if (((v[y].d - v[x].d) >> i) & 1) {
      ans = min(ans, v[y].st[i]);
      y = v[y].f[i];
    }
  }
  for (int i = kMaxL - 1; i >= 0; i--) {
    if (v[x].f[i] != v[y].f[i]) {
      ans = min({ans, v[x].st[i], v[y].st[i]});
      x = v[x].f[i], y = v[y].f[i];
    }
  }
  return x == y ? ans : min({ans, v[x].st[0], v[y].st[0]});
}

int main() {
  cin >> m >> n;
  for (int i = 1; i <= m; i++) {
    cin >> s[i].u >> s[i].v >> s[i].w;
  }
  DSU dsu(n);
  Kruskal(dsu);
  for (int i = 1; i <= n; i++) {
    if (!v[i].d) {
      Walk(i, 0);
    }
  }
  CalcF();
  int q;
  cin >> q;                                                                 
  for (int x, y; q; q--) {
    cin >> x >> y;
    cout << (dsu.Same(x, y) ? Query(x, y) : -1) << '\n';
  }
  return 0;
}
2024/5/26 12:36
加载中...