Advertisement
ivnikkk

Untitled

Dec 24th, 2022
888
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 3.71 KB | None | 0 0
  1. #define _CRT_SECURE_NO_WARNINGS
  2. #pragma GCC optimize("O3")
  3. #pragma GCC optimize("unroll-loops")
  4. #include "bits/stdc++.h"
  5. using namespace std;
  6. #define all(a) a.begin(), a.end()
  7. typedef long double ld;
  8. #define int int64_t
  9. const int inf = 1e18;
  10. struct Segtree {
  11.     struct node {
  12.         int val, ind;
  13.         node() {
  14.             val = inf, ind = -1;
  15.         }
  16.     };
  17.     vector<node> t;
  18.     int n;
  19.     Segtree(int _n) :n(_n) {
  20.         t.resize(4 * n, node());
  21.     }
  22.     node cmin(const node& lhs, const node& rhs) {
  23.         if (lhs.val > rhs.val) return rhs;
  24.         return lhs;
  25.     }
  26.     void update(int v, int tl, int tr, int pos, int x) {
  27.         if (tl == tr) {
  28.             t[v].val = x;
  29.             t[v].ind = pos;
  30.             return;
  31.         }
  32.         int tm = (tl + tr) / 2;
  33.         if (pos <= tm) { update(v * 2, tl, tm, pos, x); }
  34.         else { update(v * 2 + 1, tm + 1, tr, pos, x); }
  35.         t[v] = cmin(t[v * 2], t[v * 2 + 1]);
  36.     }
  37.     node get_min(int v, int tl, int tr, int l, int r) {
  38.         if (tl > r || tr < l) { return node(); }
  39.         if (tl >= l && tr <= r) { return t[v]; }
  40.         int tm = (tl + tr) / 2;
  41.         return cmin(get_min(v * 2, tl, tm, l, r), get_min(v * 2 + 1, tm + 1, tr, l, r));
  42.     }
  43. };
  44. int n;
  45. struct w_edge {
  46.     int val1, val2;
  47.     w_edge(int _v1, int _v2) :val1(_v1), val2(_v2) {};
  48. };
  49.  
  50. vector<vector<pair<int, w_edge>>> gr;
  51. int count_vertex = 0;
  52. void merge(int l, int r, Segtree& odd_t, Segtree& ev_t, int pred) {
  53.     if (r <= l)return;
  54.     if (l % 2 == 1) {
  55.         Segtree::node i = odd_t.get_min(1, 0, n - 1, l, r);
  56.         Segtree::node j = ev_t.get_min(1, 0, n - 1, i.ind, r);
  57.         gr[pred].push_back({ count_vertex++, w_edge(i.val, j.val) });
  58.         odd_t.update(1, 0, n - 1, i.ind, inf);
  59.         ev_t.update(1, 0, n - 1, j.ind, inf);
  60.         int now = count_vertex - 1;
  61.         if (l < i.ind - 1) { merge(l, i.ind - 1, odd_t, ev_t, now); }
  62.         merge(i.ind + 1, j.ind - 1, odd_t, ev_t, now);
  63.         if (j.ind + 1 < r) { merge(j.ind + 1, r, odd_t, ev_t, now); }
  64.     }
  65.     else {
  66.         Segtree::node i = ev_t.get_min(1, 0, n - 1, l, r);
  67.         Segtree::node j = odd_t.get_min(1, 0, n - 1, i.ind, r);
  68.         gr[pred].push_back({ count_vertex++, w_edge(i.val, j.val) });
  69.         ev_t.update(1, 0, n - 1, i.ind, inf);
  70.         odd_t.update(1, 0, n - 1, j.ind, inf);
  71.         int now = count_vertex - 1;
  72.         if (l < i.ind - 1) { merge(l, i.ind - 1, odd_t, ev_t, now); }
  73.         merge(i.ind + 1, j.ind - 1, odd_t, ev_t, now);
  74.         if (j.ind + 1 < r) { merge(j.ind + 1, r, odd_t, ev_t, now); }
  75.     }
  76. }
  77.  
  78. signed main() {
  79. #ifdef _DEBUG
  80.     freopen("input.txt", "r", stdin);
  81.     freopen("output.txt", "w", stdout);
  82. #endif
  83.     ios_base::sync_with_stdio(false);
  84.     cin.tie(nullptr);
  85.     cout.tie(nullptr);
  86.     cin >> n;
  87.     int k; cin >> k;
  88.     Segtree odd_t(n), ev_t(n);
  89.     gr.resize(n);
  90.     for (int i = 0; i < n; i++) {
  91.         int x; cin >> x;
  92.         if (i % 2 == 0) {
  93.             ev_t.update(1, 0, n - 1, i, x);
  94.             odd_t.update(1, 0, n - 1, i, inf);
  95.         }
  96.         else {
  97.             ev_t.update(1, 0, n - 1, i, inf);
  98.             odd_t.update(1, 0, n - 1, i, x);
  99.         }
  100.     }
  101.     {
  102.         Segtree::node i = ev_t.get_min(1, 0, n - 1, 0, n - 1);
  103.         Segtree::node j = odd_t.get_min(1, 0, n - 1, i.ind, n - 1);
  104.         gr[count_vertex].push_back({ count_vertex + 1, w_edge(i.val, j.val) });
  105.         count_vertex += 2;
  106.         ev_t.update(1, 0, n - 1, i.ind, inf);
  107.         odd_t.update(1, 0, n - 1, j.ind, inf);
  108.         if (0 < i.ind - 1) { merge(0, i.ind - 1, odd_t, ev_t, 1ll); }
  109.         merge(i.ind + 1, j.ind - 1, odd_t, ev_t, 1ll);
  110.         if (j.ind + 1 < n - 1) { merge(j.ind + 1, n - 1, odd_t, ev_t, 1ll); }
  111.     }
  112.     set <pair<int, pair<int, int>>> q;
  113.     q.insert({ -1,{-1, 0} });
  114.     while (!q.empty()) {
  115.         auto f = *q.begin();
  116.         if (f.first != -1) {
  117.             if (k) {
  118.                 cout << f.first << ' ';
  119.                 k--;
  120.             }
  121.             if (k) {
  122.                 cout << f.second.first << ' ';
  123.                 k--;
  124.             }
  125.             if (k == 0) {
  126.                 break;
  127.             }
  128.         }
  129.         q.erase(q.begin());
  130.         for (pair<int, w_edge>& u : gr[f.second.second]) {
  131.             q.insert({ u.second.val1,{u.second.val2, u.first} });
  132.         }
  133.     }
  134. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement