Advertisement
trungore10

code_circle_of_digit

Feb 24th, 2019
154
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 2.49 KB | None | 0 0
  1. /// solution : https://pastebin.com/JiDCvA5T
  2. #include<bits/stdc++.h>
  3. using namespace std;
  4.  
  5. typedef pair<int, int> ii;
  6. typedef unsigned long long ULL;
  7.  
  8. const int N = 4e5 + 4, LOG = 20;
  9. int n, k, Up, Down;
  10. string S;
  11.  
  12. ULL Pow[N], Hash[N];
  13.  
  14. void Build_Hash() {
  15. for (int i = 0; i <= 2*n; ++i) Pow[i] = (i == 0) ? 1 : Pow[i-1] * 31LL;
  16. for (int i = 1; i <= 2*n; ++i) Hash[i] = Hash[i-1] * 31LL + S[i] - '0';
  17. }
  18. ULL getHash(int i, int j) { return Hash[j] - Hash[i-1] * Pow[j-i+1]; }
  19.  
  20. struct data {
  21. int l, r;
  22. data() {}; data(int l, int r) : l(l), r(r) {};
  23.  
  24. bool operator < (const data &a) const {
  25. int low = 1, high = r-l+1, Equal = 0;
  26. while (low <= high) {
  27. int mid = (low + high) / 2;
  28. if (getHash(l, l+mid-1) == getHash(a.l, a.l+mid-1)) { Equal = mid; low = mid + 1; }
  29. else high = mid - 1;
  30. }
  31. // cerr << S[7] << " " << S[8] << '\n';
  32. // cerr << Equal << '\n';
  33. // cerr << "^^ " << l << " " << r << " " << a.l << " " << a.r << '\n';
  34. // cerr << "%% " << l+Equal-1 << " " << S[l+Equal-1] << '\n';
  35. // cerr << S[l+Equal] << " " << S[a.l+Equal] << '\n';
  36. if (Equal == r-l+1) return false;
  37. return S[l+Equal] < S[a.l+Equal];
  38. }
  39. };
  40.  
  41. vector<data> V;
  42. int par[N][LOG+4];
  43.  
  44. int Jump(int u, int step) {
  45. for (int i = LOG; i >= 0; --i)
  46. if (step - (1<<i) >= 0) u = par[u][i], step -= (1<<i);
  47. return (step == 0) ? u : -1;
  48. }
  49.  
  50. bool check(int mid) {
  51. for (int i = 1; i <= 2*n; ++i) par[i][0] = -1;
  52.  
  53. for (int i = 0; i <= mid; ++i) par[V[i].l][0] = V[i].r+1;
  54. for (int i = 1; i <= 2*n; ++i)
  55. if (par[i][0] == -1) par[i][0] = i + Down;
  56.  
  57. for (int j = 1; j <= LOG; ++j) for (int i = 1; i <= 2*n; ++i)
  58. par[i][j] = par[par[i][j-1]][j-1];
  59.  
  60. for (int i = 1; i <= 2*n; ++i) {
  61. int ver = Jump(i, k);
  62. if (ver - i >= n) return true;
  63. }
  64. return false;
  65. }
  66.  
  67. void sol() {
  68. Build_Hash();
  69.  
  70. if (n % k == 0) { Up = n/k; Down = n/k-1; }
  71. else { Up = n/k + 1; Down = n/k; }
  72.  
  73. for (int i = 1; i <= 2*n; ++i)
  74. if (i + Up - 1 <= 2*n) V.push_back(data(i, i+Up-1));
  75.  
  76. sort(V.begin(), V.end());
  77.  
  78. int l = 0, r = (int) V.size(), res = -1;
  79. while (l <= r) {
  80. int mid = (l + r) / 2;
  81. if (check(mid)) { res = mid; r = mid - 1; }
  82. else l = mid + 1;
  83. }
  84. cout << S.substr(V[res].l, Up) << '\n';
  85. }
  86.  
  87. int main() {
  88. ios::sync_with_stdio(0); cin.tie(0); cout.tie(0);
  89. if (fopen("input.txt", "r")) {
  90. freopen("input.txt", "r", stdin);
  91. }
  92. else if (fopen("B.in", "r")) {
  93. freopen("B.in", "r", stdin);
  94. }
  95.  
  96. cin >> n >> k >> S;
  97. S = " " + S + S;
  98.  
  99. sol();
  100.  
  101. return 0;
  102. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement