Theme
You have a box numbered 1, 2, 3,… from left to right ,..., N. You can execute four commands:
1 x y indicates moving box X to the left of box Y (ignore this command if X is already on the left of box Y ).
2 x y indicates moving box X to the right of box Y (ignore this command if X is already on the right of box Y ).
3 x y indicates the position of swap box X and Y.
4 indicates that the entire chain is reversed.
Number of boxes N and number of command lines M (1 <= n, m <= 100,000)
Question
Use arrays to simulate linked list operations, and set a forward and successor for each node.
1 is to connect X's precursor nodes to X's successor nodes, Y's precursor nodes to x nodes, and x nodes to y nodes.
2, 3, the approach is similar to 1
4. Because two operations are equal to no operation, you only need to determine whether the operation is performed an odd number of times. If yes, switch the precursor and successor of N nodes. In addition, if the first four operations are performed for an odd number of times during the execution of 1, 2, and 1, the two operations are performed for 2 and 1 respectively.
Code:
1 #include <iostream> 2 #include <algorithm> 3 #include <cstdio> 4 #include <cstring> 5 #include <utility> 6 #include <vector> 7 #include <queue> 8 using namespace std; 9 #define INF 0x3f3f3f3f 10 #define maxn 111111 11 typedef long long LL; 12 int nxt[maxn], pre[maxn]; 13 void init(int n) 14 { 15 for (int i = 1; i <= n;i++) 16 { 17 pre[i] = i - 1; 18 nxt[i] = i + 1; 19 } 20 nxt[n] = 0; 21 nxt[0] = 1; pre[0] = n; 22 } 23 void link(int l, int r) 24 { 25 pre[r] = l; nxt[l] = r; 26 } 27 int main() 28 { 29 int n, m,kase=0; 30 while (scanf("%d%d", &n, &m) != EOF) 31 { 32 int rev = 0; 33 init(n); 34 while (m--) 35 { 36 int op, x, y; 37 scanf("%d", &op); 38 if (op == 4) rev = 1 - rev; 39 else 40 { 41 scanf("%d%d", &x, &y); 42 if ((op == 1 || op == 2) && rev) op = 3 - op; 43 if (op == 3&&nxt[y] == x) swap(x, y); 44 int lx, rx, ly, ry; 45 lx = pre[x]; rx = nxt[x]; 46 ly = pre[y]; ry = nxt[y]; 47 if (op == 1) 48 { 49 if (nxt[x]==y) continue; 50 link(lx, rx); 51 link(ly, x); 52 link(x, y); 53 54 } 55 else if (op == 2) 56 { 57 if (nxt[y]==x) continue; 58 link(lx, rx); 59 link(x, ry); 60 link(y, x); 61 } 62 else 63 { 64 if (nxt[x] == y) 65 { 66 link(lx, y); 67 link(y, x); 68 link(x, ry); 69 } 70 else 71 { 72 link(lx, y); 73 link(y, rx); 74 link(ly, x); 75 link(x, ry); 76 } 77 } 78 } 79 } 80 if (rev) 81 { 82 for (int i = 1; i <= n; i++) swap(pre[i], nxt[i]); 83 } 84 int pos; 85 for (int i = 1; i <= n; i++) 86 { 87 if (pre[i] == 0) 88 { 89 pos = i; 90 break; 91 } 92 } 93 int cnt = 1; 94 LL ans = 0; 95 while (pos!=0) 96 { 97 if (cnt & 1) ans += pos; 98 pos = nxt[pos]; 99 cnt++;100 }101 printf("Case %d: %I64d\n", ++kase,ans);102 }103 return 0;104 }
View code