Advertisement
Guest User

Untitled

a guest
May 26th, 2019
89
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 4.63 KB | None | 0 0
  1. #ifndef LOCAL
  2. #pragma GCC optimize("O3")
  3. #endif
  4. #include "bits/stdc++.h"
  5. using namespace std;
  6. #define sim template < class c
  7. #define ris return * this
  8. #define dor > debug & operator <<
  9. #define eni(x) sim > typename \
  10. enable_if<sizeof dud<c>(0) x 1, debug&>::type operator<<(c i) {
  11. sim > struct rge { c b, e; };
  12. sim > rge<c> range(c i, c j) { return rge<c>{i, j}; }
  13. sim > auto dud(c* x) -> decltype(cerr << *x, 0);
  14. sim > char dud(...);
  15. struct debug {
  16. #ifdef LOCAL
  17. ~debug() { cerr << endl; }
  18. eni(!=) cerr << boolalpha << i; ris; }
  19. eni(==) ris << range(begin(i), end(i)); }
  20. sim, class b dor(pair < b, c > d) {
  21. ris << "(" << d.first << ", " << d.second << ")";
  22. }
  23. sim dor(rge<c> d) {
  24. *this << "[";
  25. for (auto it = d.b; it != d.e; ++it)
  26. *this << ", " + 2 * (it == d.b) << *it;
  27. ris << "]";
  28. }
  29. #else
  30. sim dor(const c&) { ris; }
  31. #endif
  32. };
  33. #define imie(...) " [" << #__VA_ARGS__ ": " << (__VA_ARGS__) << "] "
  34.  
  35. typedef long long ll;
  36.  
  37. #ifdef LOCAL
  38. const int nax = 105;
  39. #else
  40. const int nax = 3e5 + 5;
  41. #endif
  42. int par[nax];
  43. vector<int> children[nax];
  44. char ch[nax];
  45. int in[nax], out[nax];
  46. int depth[nax];
  47. pair<int,int> nxt_par[nax];
  48. int T = 0;
  49. int has[nax][26][2];
  50. int total[nax];
  51.  
  52. struct Node {
  53. int big, lazy;
  54. void add(int x) {
  55. big += x;
  56. lazy += x;
  57. }
  58. };
  59.  
  60. int B = 1;
  61.  
  62. struct Tree {
  63. vector<Node> tree;
  64. void rec(int id, int low, int high, int q_low, int q_high, int diff) {
  65. if(high < q_low || q_high < low) {
  66. return;
  67. }
  68. if(q_low <= low && high <= q_high) {
  69. tree[id].add(diff);
  70. return;
  71. }
  72. for(int b : {2 * id, 2 * id + 1}) {
  73. tree[b].add(tree[id].lazy);
  74. }
  75. tree[id].lazy = 0;
  76. int last_left = (low + high) / 2;
  77. rec(2 * id, low, last_left, q_low, q_high, diff);
  78. rec(2 * id + 1, last_left + 1, high, q_low, q_high, diff);
  79. tree[id].big = max(tree[2*id].big, tree[2*id+1].big);
  80. }
  81. } trees[26];
  82.  
  83. void dfs(int a) {
  84. in[a] = ++T;
  85. for(int b : children[a]) {
  86. depth[b] = depth[a] + 1;
  87. dfs(b);
  88. }
  89. out[a] = T;
  90. }
  91.  
  92. int bad;
  93. void add(int i, int A, int diff) {
  94. debug();
  95. debug() << "add" imie(i) imie(A) imie(diff);
  96. trees[A].rec(1, 0, B - 1, in[i], out[i], diff);
  97. for(pair<int,int> x = nxt_par[i]; x.first; x = nxt_par[x.first]) {
  98. debug() << "> " imie(x);
  99. if(total[x.first] < 0) {
  100. --bad;
  101. }
  102. int Z = max(has[x.first][A][0], has[x.first][A][1]);
  103. total[x.first] += Z;
  104. has[x.first][A][x.second] += diff;
  105. int Y = max(has[x.first][A][0], has[x.first][A][1]);
  106. total[x.first] -= Y; //max(has[x.first][A][0], has[x.first][A][1]);
  107. if(total[x.first] < 0) {
  108. ++bad;
  109. }
  110. if(total[x.first] < 0) {
  111. debug() << ">>> " imie(x) imie(has[x.first][A][0]) imie(has[x.first][A][1]) imie(total[x.first]);
  112. debug() << ">>>2 " imie(has[x.first][3][0]) imie(has[x.first][3][1]);
  113. }
  114. if(Z == Y) {
  115. break;
  116. }
  117. }
  118. }
  119.  
  120. int main() {
  121. int n, q;
  122. scanf("%d%d", &n, &q);
  123. for(int i = 2; i <= n; ++i) {
  124. scanf("%d %c", &par[i], &ch[i]);
  125. children[par[i]].push_back(i);
  126. }
  127. for(int i = 2; i <= n; ++i) {
  128. int p = par[i];
  129. if((int) children[p].size() >= 2) {
  130. int which = -1;
  131. if(children[p][0] == i) {
  132. which = 0;
  133. }
  134. else if(children[p][1] == i) {
  135. which = 1;
  136. }
  137. else {
  138. assert(false);
  139. }
  140. nxt_par[i] = make_pair(p, which);
  141. }
  142. else {
  143. nxt_par[i] = nxt_par[p];
  144. }
  145. }
  146. dfs(1);
  147. int should = -1;
  148. for(int i = 2; i <= n; ++i) {
  149. if(children[i].empty()) {
  150. if(should == -1) {
  151. should = depth[i];
  152. continue;
  153. }
  154. if(should != depth[i]) {
  155. debug() << "spec";
  156. while(q--) {
  157. puts("Fou");
  158. }
  159. return 0;
  160. }
  161. }
  162. }
  163. assert(should != -1);
  164. while(B <= n) {
  165. B *= 2;
  166. }
  167. for(int i = 0; i < 26; ++i) {
  168. trees[i].tree.resize(2 * B, Node{0, 0});
  169. }
  170. for(int i = 1; i <= n; ++i) {
  171. total[i] = should - depth[i];
  172. }
  173. for(int i = 2; i <= n; ++i) {
  174. if(ch[i] != '?') {
  175. int A = ch[i] - 'a';
  176. add(i, A, 1);
  177. }
  178. }
  179. debug();
  180. debug() << imie(bad);
  181. while(q--) {
  182. int i;
  183. char letter;
  184. scanf("%d %c", &i, &letter);
  185. if(ch[i] != '?') {
  186. int A = ch[i] - 'a';
  187. add(i, A, -1);
  188. }
  189. ch[i] = letter;
  190. if(ch[i] != '?') {
  191. int A = ch[i] - 'a';
  192. add(i, A, 1);
  193. }
  194. vector<int> info(26);
  195. int suma = 0;
  196. for(int j = 0; j < 26; ++j) {
  197. info[j] = trees[j].tree[1].big;
  198. suma += info[j];
  199. }
  200. debug() << imie(suma) imie(should) imie(bad);
  201. if(suma > should || bad > 0) {
  202. puts("Fou");
  203. }
  204. else {
  205. long long answer = 0;
  206. for(int j = 0; j < 26; ++j) {
  207. answer += (long long) (j + 1) * (info[j] + should - suma);
  208. }
  209. // #warning print everything
  210. // puts("Shi");
  211. printf("Shi %lld\n", answer);
  212. }
  213. // debug() << imie(suma);
  214. }
  215. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement