Problem p01882 (C++) — buggy submission, verdict: Time Limit Exceeded

//
// Created by ??? on 2017/4/20.
//

#include <algorithm>
#include <cstdio>
#include <cstring>
#include <iostream>
#include <map>
#include <set>
#include <string>
#define maxn 100100

using namespace std;

struct node {
  int val, time;
  node(int val, int time) : val(val), time(time) {}
  bool operator<(const node &A) const {
    if (val == A.val)
      return time > A.time;
    return val > A.val;
  }
};
int n, m, val;
int tval[maxn];
string op, name, mp[maxn];
map<string, int> tid;
set<node> st1, st2;

int main(void) {
  while (cin >> n) {
    st1.clear();
    st2.clear();
    tid.clear();
    for (int i = 1; i <= n; i++) {
      cin >> name >> val;
      mp[i] = name;
      tid[name] = i;
      tval[i] = val;
      st2.insert(node(val, i));
    }
    for (int i = 1; i <= n / 5; i++) {
      st1.insert(*st2.begin());
      st2.erase(st2.begin());
    }

    cin >> m;
    for (int i = 1; i <= m; i++) {
      cin >> op >> name;
      if (op == "+") {
        scanf("%d", &val);
        tval[n + i] = val;
        mp[n + i] = name;
        tid[name] = n + i;
        if ((st1.size() + st2.size() + 1) % 5 == 0) {
          st2.insert(node(val, n + i));
          node tmp = *st2.begin();
          st2.erase(st2.begin());
          st1.insert(tmp);
          if (mp[tmp.time] != name)
            cout << name << " is not working now." << endl;
          cout << mp[tmp.time] << " is working hard now." << endl;
          continue;
        }
        if (!st1.empty() && val >= (*--st1.end()).val) {
          cout << name << " is working hard now." << endl;
          node tmp = *--st1.end();
          st1.erase(--st1.end());
          st2.insert(tmp);
          cout << mp[tmp.time] << " is not working now." << endl;
          st1.insert(node(val, n + i));
          continue;
        }
        st2.insert(node(val, n + i));
        cout << name << " is not working now." << endl;

      } else {
        int ti = tid[name];
        if ((st1.size() + st2.size()) % 5 == 0) {
          if (st2.find(node(tval[ti], ti)) != st2.end()) {
            set<node>::iterator it1 = st2.find(node(tval[ti], ti));
            st2.erase(it1);
            node temp = *--st1.end();
            st1.erase(--st1.end());
            st2.insert(temp);
            cout << mp[temp.time] << " is not working now." << endl;
          } else {
            set<node>::iterator it2 = st1.find(node(tval[ti], ti));
            st1.erase(it2);
          }
        } else if (st1.find(node(tval[ti], ti)) != st1.end()) {
          set<node>::iterator it3 = st1.find(node(tval[ti], ti));
          st1.erase(it3);
          node temp = *st2.begin();
          st1.insert(temp);
          st2.erase(st2.begin());
          cout << mp[temp.time] << " is working hard now." << endl;
        } else {
          set<node>::iterator it4 = st2.find(node(tval[ti], ti));
          st2.erase(it4);
        }
      }
    }
  }
  return 0;
}

Error: TLE

Fixed submission:

#include <bits/stdc++.h>

using namespace std;

#define LL long long
#define pii pair<int, int>
#define MP make_pair
#define ls i << 1
#define rs ls | 1
#define md (ll + rr >> 1)
#define lson ll, md, ls
#define rson md + 1, rr, rs
#define mod 1000000007
#define inf 0x3f3f3f3f
#define Pi acos(-1.0)
#define PB push_back
#define eps 1e-12
#define N 200020
#define M 400020

char ss[N];
map<string, int> name;
map<int, string> rf;
int name_cnt;
struct node {
  int name_id;
  int tid, val, st;
  void input(int _tid) {
    tid = _tid;
    scanf("%s", ss);
    if (name.count(ss) == 0) {
      name[ss] = ++name_cnt;
      rf[name_cnt] = ss;
    }
    name_id = name[ss];
    scanf("%d", &val);
    st = 0;
  }
  void output() {
    if (st)
      printf("%s is not working now.\\n", rf[name_id].c_str());
    else
      printf("%s is working hard now.\\n", rf[name_id].c_str());
  }
  bool operator==(const node &b) const {
    return tid == b.tid && name_id == b.name_id && val == b.val;
  }
  bool operator<(const node &b) const {
    if (val != b.val)
      return val > b.val;
    return tid > b.tid;
  }
};

int ch[N][2], sz[N], rand_val[N], tot;
node key[N];
int n, m;
int rt;
map<int, node> mp;
int opt, now;

int creat(node v) {
  int k = ++tot;
  ch[k][0] = ch[k][1] = 0;
  sz[k] = 1;
  rand_val[k] = rand();
  key[k] = v;
  return k;
}

void push_up(int x) { sz[x] = sz[ch[x][0]] + sz[ch[x][1]] + 1; }
int cmp(int x, node &t) {
  if (key[x] == t)
    return -1;
  if (t < key[x])
    return 0;
  return 1;
}
void rot(int &x, int d) {
  int k = ch[x][!d];
  ch[x][!d] = ch[k][d];
  ch[k][d] = x;
  push_up(x);
  push_up(k);
  x = k;
}
int ins(int &x, node &v, int k) {
  if (x == 0) {
    x = creat(v);
    if (k >= 1)
      key[x].st = 0;
    else
      key[x].st = 1;
    return x;
  }
  int d = cmp(x, v);
  if (d == 1)
    k -= 1 + sz[ch[x][0]];
  int ret = ins(ch[x][d], v, k);
  if (rand_val[ch[x][d]] > rand_val[x])
    rot(x, d ^ 1);
  push_up(x);
  return ret;
}
int ttt;
void check(int &x, int k, int msk) {
  if (x == 0)
    return;
  if (k <= sz[ch[x][0]])
    check(ch[x][0], k, msk);
  else if (k == sz[ch[x][0]] + 1) {
    if (key[x].st == msk)
      return;
    key[x].st = msk;
    if (opt && x != ttt)
      key[x].output();
    return;
  }
  check(ch[x][1], k - sz[ch[x][0]] - 1, msk);
}

void insert(node t) {
  int k = (sz[rt] + 1) / 5;
  ttt = ins(rt, t, k);
  if (opt)
    key[ttt].output();

  for (int i = k - 1; i <= k; ++i) {
    if (i >= 1 && i <= sz[rt]) {
      check(rt, i, 0);
    }
  }
  if (k + 1 >= 1 && k + 1 <= sz[rt]) {
    check(rt, k + 1, 1);
  }
}
void del(int &x, node &v) {
  if (x == 0)
    return;
  int d = cmp(x, v);
  if (d == -1) {
    if (!ch[x][0])
      x = ch[x][1];
    else if (!ch[x][1])
      x = ch[x][0];
    else {
      int d2 = rand_val[ch[x][0]] > rand_val[ch[x][1]] ? 1 : 0;
      rot(x, d2);
      del(ch[x][d2], v);
    }
  } else
    del(ch[x][d], v);
  if (x)
    push_up(x);
}

void del(node t) {
  del(rt, t);
  int k = sz[rt] / 5;
  for (int i = k - 1; i <= k; ++i) {
    if (i >= 1 && i <= sz[rt]) {
      check(rt, i, 0);
    }
  }
  if (k + 1 >= 1 && k + 1 <= sz[rt])
    check(rt, k + 1, 1);
}

int main() {
  scanf("%d", &n);
  now = 0;
  for (int i = 1; i <= n; ++i) {
    now++;
    node t;
    t.input(i);
    insert(t);
    mp[t.name_id] = t;
  }
  opt = 1;
  scanf("%d", &m);
  for (int i = 1; i <= m; ++i) {
    now++;
    char op[5];
    scanf("%s", op);
    if (op[0] == '-') {
      scanf("%s", ss);
      del(mp[name[ss]]);
    } else {
      node t;
      t.input(now);
      insert(t);
      mp[t.name_id] = t;
    }
  }
  return 0;
}