Advertisement
Alex239

Untitled

May 20th, 2018
157
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 3.00 KB | None | 0 0
  1. #include <bits/stdc++.h>
  2. #include "nonintersecting.h"
  3. #include <vector>
  4.  
  5. using namespace std;
  6. using pii = pair<int, int>;
  7.  
  8. using nagai = long long;
  9.  
  10. const int N = 100000;
  11. int mx[2 * N];
  12.  
  13. int oo = 1e9;
  14.  
  15. int getmx(int l, int r)
  16. {
  17.     l += N;
  18.     r += N;
  19.     int ans = -1;
  20.     while (l < r)
  21.     {
  22.         if (l & 1)
  23.             ans = max(ans, mx[l++]);
  24.         if (r & 1)
  25.             ans = max(ans, mx[--r]);
  26.         l /= 2, r /= 2;
  27.     }
  28.     return ans;
  29. }
  30.  
  31. void mod(int x, int y)
  32. {
  33.     x += N;
  34.     mx[x] = y;
  35.     while (x)
  36.     {
  37.         mx[x >> 1] = max(mx[x], mx[x ^ 1]);
  38.         x /= 2;
  39.     }
  40. }
  41.  
  42. void init()
  43. {
  44.     fill(mx, mx + 2 * N, -1);
  45. }
  46.  
  47. int n;
  48.  
  49. vector<int> findlds(vector<int>& a, vector<bool>& del)
  50. {
  51.     init();
  52.     vector<int> dp(n, -1);
  53.     for (int i = 0; i < n; ++i)
  54.     {
  55.         if (del[i])
  56.             continue;
  57.         dp[i] = max(1, getmx(a[i] + 1, n) + 1);
  58.         mod(a[i], dp[i]);
  59.     }
  60.     vector<int> ans;
  61.     int curdp = *max_element(dp.begin(), dp.end());
  62.     if (curdp < 0)
  63.         return {};
  64.     int last = -1;
  65.     for (int i = n - 1; i >= 0; --i)
  66.     {
  67.         if (dp[i] == curdp && a[i] > last)
  68.             last = a[i], --curdp, ans.push_back(i);
  69.     }
  70.     reverse(ans.begin(), ans.end());
  71.     return ans;
  72. }
  73.  
  74. struct gener
  75. {
  76.     vector<int> dp1;
  77.     vector<vector<int>> mem;
  78.     vector<int> a;
  79.     int lis;
  80.     gener(vector<int>& a)
  81.         : a(a)
  82.     {
  83.         init();
  84.         dp1.resize(n);
  85.         for (int i = n - 1; i >= 0; --i)
  86.         {
  87.             dp1[i] = max(1, getmx(a[i] + 1, n) + 1);
  88.             mod(a[i], dp1[i]);
  89.         }
  90.         lis = *max_element(dp1.begin(), dp1.end());
  91.         mem.resize(n + 1);
  92.         for (int i = 0; i < n; ++i)
  93.             mem[dp1[i]].push_back(i);
  94.     }
  95.     vector<int> gen()
  96.     {
  97.         vector<int> curkek;
  98.         int lastind = -1;
  99.         int lastmem = -1;
  100.         for (int i = 0; i < lis; ++i)
  101.         {
  102.             vector<int> lst;
  103.             for (int x : mem[lis - i])
  104.                 if (x > lastind && a[x] > lastmem)
  105.                     lst.push_back(x);
  106.             int x = lst[rand() % lst.size()];
  107.             curkek.push_back(x);
  108.             lastind = x;
  109.             lastmem = a[x];
  110.         }
  111.         return curkek;
  112.     }
  113. };
  114.  
  115. nagai myt()
  116. {
  117.     return clock() * 1000 / CLOCKS_PER_SEC;
  118. }
  119.  
  120.  
  121. pair<std::vector<int>, std::vector<int>> nonintersecting(const std::vector<int> &P) {
  122.     vector<int> a = P;
  123.     n = a.size();
  124.     for (int& x : a)
  125.         --x;
  126.     pair<vector<int>, vector<int>> ans;
  127.     vector<bool> del(n);
  128.     auto mark = [&](vector<int>& kek, bool rev)
  129.     {
  130.         fill(del.begin(), del.end(), 0);
  131.         for (int x : kek)
  132.         {
  133.             if (rev)
  134.                 x = n - x - 1;
  135.             del[x] = true;
  136.         }
  137.     };
  138.     gener g1(a);
  139.     auto a1 = a;
  140.     reverse(a1.begin(), a1.end());
  141.     gener g2(a1);
  142.     int abc = g1.gen().size();
  143.     int def = g2.gen().size();
  144.     while (true)
  145.     {
  146.         auto x = g1.gen();
  147.         mark(x, false);
  148.         auto lds = findlds(a, del);
  149.         if (lds.size() == def)
  150.         {
  151.             ans = {x, lds};
  152.             break;
  153.         }
  154.         x = g2.gen();
  155.         reverse(x.begin(), x.end());
  156.         for (auto& y : x)
  157.             y = n - y - 1;
  158.         mark(x, true);
  159.         auto lis = findlds(a1, del);
  160.         if (lis.size() == abc)
  161.         {
  162.             for (auto& x : lis)
  163.                 x = n - x - 1;
  164.             reverse(lis.begin(), lis.end());
  165.             ans = {lis, x};
  166.             break;
  167.         }
  168.         if (myt() > 2950)
  169.             break;
  170.     }
  171.     for (auto& x : ans.first)
  172.         ++x;
  173.     for (auto& x : ans.second)
  174.         ++x;
  175.     return ans;
  176. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement