bibaboba12345

Untitled

Nov 20th, 2022
133
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 5.38 KB | None | 0 0
  1. // clang-format off
  2. #define _CRT_SECURE_NO_WARNINGS
  3. #include <iostream>
  4. #include <iomanip>
  5. #include <bitset>
  6. #include <vector>
  7. #include <algorithm>
  8. #include <random>
  9. #include <map>
  10. #include <string>
  11. #include <set>
  12. #include <deque>
  13. #include <cassert>
  14.  
  15.  
  16.  
  17. const int N = 1e5 + 7, A = 26, C = 2, MOD = 998244353, bl = 1000;
  18. const long long INF = 1e18;
  19. using namespace std;
  20. using ll = long long;
  21. using ld = long double;
  22.  
  23. const ld EPS = 1e-9;
  24.  
  25. int a[N], n;
  26.  
  27. struct Block {
  28. vector<int> elems;
  29. int cnt[N];
  30. int size;
  31. int count(int l, int r, int x) {
  32. if (r == size - 1 && l == 0) {
  33. return cnt[x];
  34. }
  35. int ans = 0;
  36. for (int i = l; i <= r; i++) {
  37. if (elems[i] == x) {
  38. ans++;
  39. }
  40. }
  41. return ans;
  42. }
  43.  
  44. void clear() {
  45. for (int i = 0; i < size; i++) {
  46. cnt[elems[i]]--;
  47. elems[i] = 0;
  48. }
  49. elems.clear();
  50. size = 0;
  51. }
  52.  
  53. void split(int r, Block* res) {
  54. res->clear();
  55. for (int i = r; i < size; i++) {
  56. cnt[elems[i]]--;
  57. res->cnt[elems[i]]++;
  58. }
  59. res->size = size - r;
  60. res->elems.resize(size - r);
  61. for (int i = r; i < size; i++) {
  62. res->elems[i - r] = elems[i];
  63. elems[i] = 0;
  64. }
  65. elems.resize(r);
  66. size = r;
  67. }
  68. };
  69.  
  70. Block blocks[500];
  71. int CNT = 0;
  72. Block* nw() {
  73. if (CNT == 499) {
  74. cout << "ABOBA";
  75. exit(0);
  76. }
  77. return &blocks[CNT++];
  78. }
  79.  
  80. struct SplitRebuildDecomp {
  81. vector<Block*> b;
  82. int size;
  83. void destroy() {
  84. for (int I = 0; I < b.size(); I++) {
  85. b[I]->clear();
  86. }
  87. b.clear();
  88. CNT = 0;
  89. }
  90.  
  91. void build(int n) {
  92. size = n;
  93. int cnt = 0;
  94. destroy();
  95. for (int i = 0; i < n; i++) {
  96. if (i % bl == 0) {
  97. b.push_back(nw());
  98. }
  99. b[b.size() - 1]->cnt[a[i]]++;
  100. b[b.size() - 1]->elems.push_back(a[i]);
  101. b[b.size() - 1]->size++;
  102. }
  103. }
  104.  
  105. void print(int n) {
  106. int i = 0;
  107. for (int I = 0; I < b.size(); I++) {
  108. auto u = b[I];
  109. for (int j = 0; j < u->size; j++) {
  110. a[i] = u->elems[j];
  111. i++;
  112. }
  113. }
  114. }
  115.  
  116. void rebuild(int n) {
  117. print(n);
  118. build(n);
  119. }
  120.  
  121. int FindL(int l) {
  122. int lft = 0;
  123. for (int i = 0; i < b.size(); i++) {
  124. if (lft == l) {
  125. return i;
  126. }
  127. lft += b[i]->size;
  128. }
  129. assert(false);
  130. }
  131.  
  132. int FindR(int r) {
  133. int lft = 0;
  134. for (int i = 0; i < b.size(); i++) {
  135. if (lft + b[i]->size - 1 == r) {
  136. return i;
  137. }
  138. lft += b[i]->size;
  139. }
  140. assert(false);
  141. }
  142.  
  143. void split(int r) {
  144. if (r == 0) {
  145. return;
  146. }
  147. int sz = 0;
  148. int i1 = -1;
  149. Block* newB = nw();
  150. for (int i = 0; i < b.size(); i++) {
  151. if (sz + b[i]->size == r) {
  152. CNT--;
  153. return;
  154. }
  155. if (sz + b[i]->size >= r) {
  156. b[i]->split(r - sz, newB);
  157. i1 = i + 1;
  158. break;
  159. }
  160. sz += b[i]->size;
  161. }
  162. for (i1; i1 < b.size(); i1++) {
  163. swap(newB, b[i1]);
  164. }
  165. b.push_back(newB);
  166. }
  167.  
  168. void cyclic(int l, int r) {
  169. for (int i = r; i > l; i--) {
  170. swap(b[i], b[i - 1]);
  171. }
  172. }
  173.  
  174. void cyc(int l, int r) {
  175. split(l);
  176. split(r);
  177. split(r + 1);
  178. l = FindL(l);
  179. r = FindR(r);
  180. cyclic(l, r);
  181. if (b.size() >= 400) {
  182. rebuild(size);
  183. }
  184. }
  185.  
  186. int get(int l, int r, int k) {
  187. int lft = 0;
  188. int answ = 0;
  189. for (int i = 0; i < b.size(); i++) {
  190. int rgt = lft + b[i]->size - 1;
  191. int L = max(l, lft), R = min(r, rgt);
  192. if (L <= R) {
  193. answ += b[i]->count(L - lft, R - lft, k);
  194. }
  195. lft = rgt + 1;
  196. }
  197. return answ;
  198. }
  199. };
  200.  
  201. SplitRebuildDecomp S;
  202.  
  203. signed main() {
  204. #ifdef _DEBUG
  205. freopen("input.txt", "r", stdin);
  206. #else
  207. std::ios::sync_with_stdio(false);
  208. cin.tie(0);
  209. #endif
  210. cin >> n;
  211. for (int i = 0; i < n; i++) {
  212. cin >> a[i];
  213. }
  214. S.build(n);
  215. int q;
  216. cin >> q;
  217. int lastans = 0;
  218. for (int I = 0; I < q; I++) {
  219. int tp;
  220. cin >> tp;
  221. if (tp == 1) {
  222. int l, r;
  223. cin >> l >> r;
  224. l = (l + lastans - 1) % n + 1;
  225. r = (r + lastans - 1) % n + 1;
  226. l--;
  227. r--;
  228. if (l > r) {
  229. swap(l, r);
  230. }
  231. S.cyc(l, r);
  232. }
  233. else {
  234. int l, r, k;
  235. cin >> l >> r >> k;
  236. l = (l + lastans - 1) % n + 1;
  237. r = (r + lastans - 1) % n + 1;
  238. k = (k + lastans - 1) % n + 1;
  239. l--;
  240. r--;
  241. if (l > r) {
  242. swap(l, r);
  243. }
  244. lastans = S.get(l, r, k);
  245. cout << lastans << "\n";
  246. }
  247. }
  248. }
Advertisement
Add Comment
Please, Sign In to add comment