Untitled

 avatar
unknown
plain_text
a month ago
2.6 kB
3
Indexable
#include <iostream>
#include <string>
#include <algorithm>
#include <vector>
#include <queue>
#include <map>
#include <set>
#include <stack>
#include <iomanip>
#include <cmath>
#include <cstring>
#include <numeric>
#include <cstdio>
#include <list>
#include <cassert>
#include <climits>
#include <bitset>
#include <functional>

using namespace std;

#define IN(type, name) \
  type name; \
  cin >> name;

#define For(var, constant, init) for (int var = init; var < constant; var++)

#define Sp << ' ' <<
#define End << '\n'

#define PI 3.141592653589793238462643383279502884L

#define ll long long
#define ull unsigned long long
#define uint unsigned int
#define ld long double

#define MOD 1000000007

typedef vector<int> vint;
typedef vector<ll> vll;
typedef pair<int, int> pint;
typedef pair<ll, ll> pll;

struct UF {
  vint p;
  vint sizes;

  UF(int size) {
    p.resize(size, -1);
    sizes.resize(size, 1);
    For(i, size, 0) p[i] = i;
  }

  int find(int a) {
    int current = a;
    while(p[current] != current)
      current = p[current];

    while(a != current) {
      int tmp = a;
      a = p[a];
      p[tmp] = current;
    }

    return a;
  }

  void unify(int a, int b) {
    int r1 = find(a);
    int r2 = find(b);

    if (r1 == r2) return;

    int n = (r1 == 0 ? r1 : r2);
    int m = (n == r1 ? r2 : r1);
    p[m] = n;
    sizes[n] += sizes[m];
  }

};

int main() {
  ios::sync_with_stdio(0);
  cin.tie(0);

  IN(int, n);
  IN(int, m);

  vint ids(n);
  for(int &id : ids) cin >> id, id--;

  vector<pint> edges(m);
  for(auto &edge : edges) {
    cin >> edge.first >> edge.second;
    edge.first--; edge.second--;
    edge = {ids[edge.first], ids[edge.second]};
    if (edge.first > edge.second) swap(edge.first, edge.second);
  }

  sort(edges.begin(), edges.end(), [](pint &p1, pint &p2) -> bool {
    return make_pair(p1.second, p1.first) < make_pair(p2.second, p2.first);
  });

  sort(ids.begin(), ids.end());
  int l = 0, r = n - 1, x = 0;
  while(l <= r) {
    int mid = l + (r - l) / 2;
    if (ids[mid] == mid) {x = mid; l = mid + 1;}
    else r = mid - 1;
  }

  UF uf(ids[x] + 1);
  int mx = 0, best = 1;
  for(auto &e : edges) {
    if (e.first > ids[x] + 1 || e.second > ids[x] + 1) continue;
    if (uf.find(e.first) != uf.find(e.second)) {
      uf.unify(e.first, e.second);
      if (uf.find(e.first) == 0) {
        mx = max(mx, e.second);
        if (uf.sizes[0] == mx + 1) best = mx + 1;
      }
    }    
  }

  cout << best;

}
Leave a Comment