Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #include <bits/stdc++.h>
- using namespace std;
- struct edge {
- unsigned short int v, u;
- double e;
- bool operator<(edge b) {
- return e < b.e;
- }
- edge(unsigned short int _v = 0, unsigned short int _u = 0, long double _e = 0) {
- v = _v;
- u = _u;
- e = _e;
- }
- };
- const int C = 330;
- array <unsigned short int, 3> p[50050];
- vector <edge> e;
- long double dis(array <unsigned short int, 3> a, array <unsigned short int, 3> b) {
- return sqrt((a[0] - b[0]) * (a[0] - b[0]) + (a[1] - b[1]) * (a[1] - b[1]));
- }
- int dsu[50050];
- int ran[50050];
- int get(int v) {
- if (dsu[v] == v) {
- return v;
- }
- else {
- return dsu[v] = get(dsu[v]);
- }
- }
- void unite(int a, int b) {
- a = get(a);
- b = get(b);
- if (ran[a] < ran[b]) {
- dsu[a] = b;
- }
- else {
- dsu[b] = dsu[a];
- if (ran[a] == ran[b]) {
- ran[b]++;
- }
- }
- }
- bool cmp(array <int, 3> a, array <int, 3> b) {
- return a[1] < b[1] || (a[1] == b[1] && a[0] < b[0]);
- }
- int32_t main() {
- e.reserve(50000 * C);
- ios_base::sync_with_stdio(false);
- cin.tie(NULL);
- cout.tie(NULL);
- for (int i = 0; i < 50050; i++) {
- dsu[i] = i;
- }
- int n;
- cin >> n;
- for (int i = 0; i < n; i++) {
- cin >> p[i][0] >> p[i][1];
- p[i][2] = i;
- }
- sort(p, p + n);
- for (int i = 0; i < n; i++) {
- for (int j = i + 1; j < min(n, i + C + 200); j++) {
- double d = dis(p[i], p[j]);
- if (n > 10000 && d > 1000) {
- continue;
- }
- e.push_back({p[i][2], p[j][2], d});
- }
- }
- sort(e.begin(), e.end());
- vector <array <int, 2> > ans;
- long double ansv = 0;
- for (auto ed : e) {
- if (get(ed.v) == get(ed.u)) {
- continue;
- }
- else {
- ansv += ed.e;
- ans.push_back({ed.v, ed.u});
- unite(ed.v, ed.u);
- }
- }
- cout.precision(20);
- cout << fixed;
- cout << ansv << "\n";
- for (auto z : ans) {
- cout << z[0] + 1 << " " << z[1] + 1 << "\n";
- }
- return 0;
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement