Submission #656237

# Submission time Handle Problem Language Result Execution time Memory
656237 2022-11-06T15:39:12 Z 600Mihnea Inside information (BOI21_servers) C++17
50 / 100
490 ms 114584 KB
bool home = 0;
#include <bits/stdc++.h>

using namespace std;

const int N = 240000 + 7;
const int K = 20;
int n;
int k;
vector<pair<int, int>> gg[N];
vector<pair<int, int>> q2[N];
int q1[N];
int p[N];
int pskip[K][N];
int dep[N];
int euler_tour[2 * N];
int tour_sz;
int first_time_on_tour[N];
int last_time_on_tour[N];
int lg2[2 * N];
int idup[N];
//vector<int> g[N];
pair<int, int> tab_lca[2 * N][K];
vector<int> who_have_id[N];
int who_has_id[N];

void dfs_lca(int a, int par = 0)
{
  p[a] = par;
  euler_tour[++tour_sz] = a;
  first_time_on_tour[a] = last_time_on_tour[a] = tour_sz;
  vector<pair<int, int>> ngg;
  for (auto& it : gg[a])
  {
    int b = it.first;
    int i = it.second;

    if (b == par) {
      continue;
    }
    ngg.push_back(it);
    who_has_id[i] = b;
    idup[b] = i;
    dep[b] = 1 + dep[a];
    dfs_lca(b, a);
    euler_tour[++tour_sz] = a;
    last_time_on_tour[a] = tour_sz;
  }
  gg[a] = ngg;
}

void lcaTM()
{
  dfs_lca(1);
  for (int i = 2; i <= tour_sz; i++)
  {
    lg2[i] = 1 + lg2[i / 2];
  }
  for (int i = 1; i <= tour_sz; i++)
  {
    tab_lca[i][0] = { dep[euler_tour[i]], euler_tour[i] };
  }
  for (int k = 1; (1 << k) <= tour_sz; k++)
  {
    for (int i = 1; i + (1 << k) - 1 <= tour_sz; i++)
    {
      tab_lca[i][k] = min(tab_lca[i][k - 1], tab_lca[i + (1 << (k - 1))][k - 1]);
    }
  }
}

int lca(int a, int b)
{
  if (first_time_on_tour[a] > last_time_on_tour[b])
  {
    swap(a, b);
  }
  a = first_time_on_tour[a];
  b = last_time_on_tour[b];
  int k = lg2[b - a + 1];
  return min(tab_lca[a][k], tab_lca[b - (1 << k) + 1][k]).second;
}

int goup(int a, int cnt) {
  assert(cnt >= 0);
  for (int i = 0; i < K; i++) {
    if (cnt & (1 << i)) {
      a = pskip[i][a];
    }
  }
  return a;
}

int sol[N];
int tp[N];
int inc[N];
int dcr[N];
int cnt[N];

void dfs2(int a) {
  inc[a] = max(inc[a], 1);
  dcr[a] = max(dcr[a], 1);
  for (auto& it : gg[a]) {
    int b = it.first;
    if (b == p[a]) {
      continue;
    }
    if (idup[a] < idup[b]) {
      inc[b] = 1 + inc[a];
    }
    else {
      dcr[b] = 1 + dcr[a];
    }
    dfs2(b);
  }  ///cout<<"vis "<<a<<" : "<<inc[a]<<" vs "<<dcr[a]<<"\n";
}

bool blocked[N];
vector<int> cq[N];
vector<pair<int, int>> realg[N];
int score[N];
int total_score;
int curpar[N];
int when[N];
int goval[N];

struct T {
  int start;
  int finish;
};

vector<T> all;

void compute_score(int a, int p = -1) {
  score[a] = 1 + (int) cq[a].size();
  for (auto &it : realg[a]) {
    int b = it.first, i = it.second;
    if (blocked[b] || b == p) {
      continue;
    }
    compute_score(b, a);
    score[a] += score[b];
  }
}

int fndcen(int a, int p = -1) {
  int mx = total_score - score[a];
  for (auto &it : realg[a]) {
    int b = it.first, i = it.second;
    if (blocked[b] || b == p) {
      continue;
    }
    mx = max(mx, score[b]);
  }
  if (mx <= total_score / 2) {
    return a;
  }
  for (auto &it : realg[a]) {
    int b = it.first, i = it.second;
    if (blocked[b] || b == p) {
      continue;
    }
    if (mx == score[b]) {
      return fndcen(b, a);
    }
  }
  assert(0);
}

void dfsfromcen(int a, int p, int group, int cr, bool ok, int gval) {
  if (ok) {
    all.push_back({gval, cr});
  }
  curpar[a] = p;
  for (auto &it : realg[a]) {
    int b = it.first, i = it.second;
    if (blocked[b] || b == p) {
      continue;
    }
    when[b] = i;
    bool new_ok = ok;
    if (!(cr < i)) {
      new_ok = 0;
    }
    dfsfromcen(b, a, group, i, new_ok, gval);
  }
}

int kekdfs(int a, int p, int last, int t) {
  int sol = 0;
  for (auto &it : realg[a]) {
    int b = it.first, i = it.second;
    if (blocked[b] || b == p) {
      continue;
    }
    if (last < i) {
      if (i < t) {
        sol++;
      }
      sol += kekdfs(b, a, i, t);
    }
  }
  return sol;
}

vector<int> guys;
vector<pair<int, int>> ts;

void dfsexplore(int a, int p, int lst, bool is, int send) {
  for (auto &it : realg[a]) {
    int b = it.first, i = it.second;
    if (blocked[b] || b == p) {
      continue;
    }
    bool new_is = is;
    if (!(lst > i)) {
      new_is = 0;
    }
    dfsexplore(b, a, i, new_is, send);
  }
  if (p && is) {
    assert(curpar[a] == p);
    for (auto &T : cq[a]) {
      sol[T] += (send < T);
      ts.push_back({T, send});
    }
  }
}

void cdecomp(int a) {
  ts.clear();
  all.clear();
  compute_score(a);
  total_score = score[a];
  a = fndcen(a);

  guys.clear();
  int cnt_guys = 0;
  for (auto &it : realg[a]) {
    int b = it.first, i = it.second;
    if (blocked[b]) {
      continue;
    }
    cnt_guys++;
    when[b] = i;
    goval[b] = i;
    guys.push_back(b);
    dfsfromcen(b, a, i, i, 1, i);
  }
  assert((int) guys.size() == cnt_guys);
  curpar[a] = 0;
  for (auto &jj : ts) {
    int T = jj.first, send = jj.second;
    break;
    for (auto &some : all) {
      if (send < some.start && some.finish < T) {
        sol[T]++;
      }
    }
  }
  {
    /// the case for a
    for (auto &T : cq[a]) {
      sol[T] += kekdfs(a, 0, -1, T);
    }
  }
  {
    /// the case for the others and it also going through a
    /// it stops at a

    for (auto &it : realg[a]) {
      int b = it.first, i = it.second;
      if (blocked[b]) {
        continue;
      }
      dfsexplore(b, a, i, 1, i);
    }
  }

  blocked[a] = 1;
  for (auto &it : realg[a]) {
    int b = it.first, i = it.second;
    if (blocked[b]) {
      continue;
    }
    cdecomp(b);
  }
}

int main() {
  if (!home) {
    ios::sync_with_stdio(0), cin.tie(0), cout.tie(0);
  } else {
    freopen("___input___.txt", "r", stdin);
  }
  cin >> n >> k;

  int cnt3 = 0;
  for (int i = 1; i <= n + k - 1; i++) {
    string s;
    cin >> s;
    assert(s == "S" || s == "Q" || s == "C");
    if (s == "S") {
      tp[i] = 2;
      int a, b;
      cin >> a >> b;
      ///g[a].push_back(b);
      ///g[b].push_back(a);
      gg[a].push_back({ b, i });
      gg[b].push_back({ a, i });
      sol[i] = -1;
    }
    if (s == "Q") {
      int a, b;
      cin >> a >> b;
      if (a == b) {
        tp[i] = 1;
        sol[i] = 1;
      }
      else {
        q2[a].push_back({ b, i });
        tp[i] = 1;
        sol[i] = -2;
      }
    }
    if (s == "C") {
      cnt3++;
      int a;
      cin >> a;
      cq[a].push_back(i);
      ///   cout<<i<<" = "<<a<<"\n";
      q1[i] = a;
      sol[i] = -3;
      tp[i] = 3;
    }
  }
  for (int i = 1; i <= n; i++) {
    realg[i] = gg[i];
  }

  lcaTM();
  dfs2(1);
  cdecomp(1);
  /// solve q1 for the general case

  for (int i = 1; i <= n; i++) {
    pskip[0][i] = p[i];
  }
  for (int k = 1; k < K; k++) {
    for (int i = 1; i <= n; i++) {
      pskip[k][i] = pskip[k - 1][pskip[k - 1][i]];
    }
  }


  for (int a = 1; a <= n; a++) {
    for (auto& it : q2[a]) {
      int b = it.first, i = it.second;
      /**

      **/
      /// drumul de la b la a e crescator?
      vector<int> guys_x, guys_y;
      int x = a, y = b, z;
      swap(x, y);
      z = lca(x, y);
      int last = -1;
      if (y != z) {
        last = idup[y];
      }
      else {
        last = idup[goup(x, dep[x] - dep[z] - 1)];
      }
      bool ok = 1;
      ok &= (inc[y] >= dep[y] - dep[z]);
      ok &= (dcr[x] >= dep[x] - dep[z]);
      if (x != z && y != z) {
        ok &= (idup[goup(x, dep[x] - dep[z] - 1)] <= idup[goup(y, dep[y] - dep[z] - 1)]);
      }
      ok &= (last < i);
      sol[i] = ok;
    }
  }

  const int INF = (int)1e9 + 7;

  int cnt_2 = 0;
  for (int i = 1; i <= n + k - 1 && cnt3 != 0; i++) {
    if (tp[i] == 2) {
      cnt_2++;
      int cnt_down = max(1, inc[who_has_id[i]] - 1);
      int vertex = who_has_id[i];
      for (int j = 1; j <= cnt_down; j++) {
        cnt[vertex]++;
        vertex = p[vertex];
      }
    }
  }
  if (cnt3) {
    assert(cnt_2 == n - 1);
  }
  for (int i = 1; i <= n + k - 1; i++) {
    if (tp[i] == 1) {
      assert(sol[i] == 0 || sol[i] == 1);
      if (sol[i] == 1) {
        cout << "yes\n";
      }
      else {
        cout << "no\n";
      }
    }
    if (tp[i] == 3) {
      cout << sol[i] + 4 << "\n";
    }
  }

  return 0;
}

Compilation message

servers.cpp: In function 'void compute_score(int, int)':
servers.cpp:137:23: warning: unused variable 'i' [-Wunused-variable]
  137 |     int b = it.first, i = it.second;
      |                       ^
servers.cpp: In function 'int fndcen(int, int)':
servers.cpp:149:23: warning: unused variable 'i' [-Wunused-variable]
  149 |     int b = it.first, i = it.second;
      |                       ^
servers.cpp:159:23: warning: unused variable 'i' [-Wunused-variable]
  159 |     int b = it.first, i = it.second;
      |                       ^
servers.cpp: In function 'void cdecomp(int)':
servers.cpp:282:23: warning: unused variable 'i' [-Wunused-variable]
  282 |     int b = it.first, i = it.second;
      |                       ^
servers.cpp: In function 'int main()':
servers.cpp:385:13: warning: unused variable 'INF' [-Wunused-variable]
  385 |   const int INF = (int)1e9 + 7;
      |             ^~~
servers.cpp:294:12: warning: ignoring return value of 'FILE* freopen(const char*, const char*, FILE*)' declared with attribute 'warn_unused_result' [-Wunused-result]
  294 |     freopen("___input___.txt", "r", stdin);
      |     ~~~~~~~^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
# Verdict Execution time Memory Grader output
1 Correct 53 ms 31736 KB Output is correct
2 Correct 68 ms 34076 KB Output is correct
3 Correct 57 ms 34068 KB Output is correct
4 Correct 74 ms 34252 KB Output is correct
5 Correct 61 ms 34092 KB Output is correct
6 Correct 68 ms 33920 KB Output is correct
# Verdict Execution time Memory Grader output
1 Correct 53 ms 31736 KB Output is correct
2 Correct 68 ms 34076 KB Output is correct
3 Correct 57 ms 34068 KB Output is correct
4 Correct 74 ms 34252 KB Output is correct
5 Correct 61 ms 34092 KB Output is correct
6 Correct 68 ms 33920 KB Output is correct
7 Incorrect 48 ms 31880 KB Extra information in the output file
8 Halted 0 ms 0 KB -
# Verdict Execution time Memory Grader output
1 Correct 61 ms 31876 KB Output is correct
2 Correct 277 ms 100092 KB Output is correct
3 Correct 279 ms 99996 KB Output is correct
# Verdict Execution time Memory Grader output
1 Correct 61 ms 31876 KB Output is correct
2 Correct 277 ms 100092 KB Output is correct
3 Correct 279 ms 99996 KB Output is correct
4 Incorrect 51 ms 31992 KB Extra information in the output file
5 Halted 0 ms 0 KB -
# Verdict Execution time Memory Grader output
1 Correct 45 ms 31840 KB Output is correct
2 Correct 341 ms 114148 KB Output is correct
3 Correct 337 ms 114148 KB Output is correct
4 Correct 301 ms 114456 KB Output is correct
# Verdict Execution time Memory Grader output
1 Correct 45 ms 31840 KB Output is correct
2 Correct 341 ms 114148 KB Output is correct
3 Correct 337 ms 114148 KB Output is correct
4 Correct 301 ms 114456 KB Output is correct
5 Incorrect 46 ms 31752 KB Extra information in the output file
6 Halted 0 ms 0 KB -
# Verdict Execution time Memory Grader output
1 Correct 49 ms 31756 KB Output is correct
2 Correct 335 ms 97284 KB Output is correct
3 Correct 311 ms 96312 KB Output is correct
# Verdict Execution time Memory Grader output
1 Correct 49 ms 31756 KB Output is correct
2 Correct 335 ms 97284 KB Output is correct
3 Correct 311 ms 96312 KB Output is correct
4 Incorrect 58 ms 31748 KB Extra information in the output file
5 Halted 0 ms 0 KB -
# Verdict Execution time Memory Grader output
1 Correct 46 ms 31820 KB Output is correct
2 Correct 345 ms 114164 KB Output is correct
3 Correct 360 ms 114144 KB Output is correct
4 Correct 299 ms 114584 KB Output is correct
5 Correct 48 ms 31848 KB Output is correct
6 Correct 309 ms 97164 KB Output is correct
7 Correct 293 ms 96292 KB Output is correct
8 Correct 418 ms 97888 KB Output is correct
9 Correct 403 ms 97640 KB Output is correct
10 Correct 480 ms 103144 KB Output is correct
11 Correct 478 ms 102124 KB Output is correct
# Verdict Execution time Memory Grader output
1 Correct 46 ms 31820 KB Output is correct
2 Correct 345 ms 114164 KB Output is correct
3 Correct 360 ms 114144 KB Output is correct
4 Correct 299 ms 114584 KB Output is correct
5 Correct 48 ms 31848 KB Output is correct
6 Correct 309 ms 97164 KB Output is correct
7 Correct 293 ms 96292 KB Output is correct
8 Correct 418 ms 97888 KB Output is correct
9 Correct 403 ms 97640 KB Output is correct
10 Correct 480 ms 103144 KB Output is correct
11 Correct 478 ms 102124 KB Output is correct
12 Incorrect 55 ms 31764 KB Extra information in the output file
13 Halted 0 ms 0 KB -
# Verdict Execution time Memory Grader output
1 Correct 53 ms 31760 KB Output is correct
2 Correct 66 ms 34036 KB Output is correct
3 Correct 59 ms 34060 KB Output is correct
4 Correct 68 ms 34196 KB Output is correct
5 Correct 60 ms 34124 KB Output is correct
6 Correct 68 ms 33880 KB Output is correct
7 Correct 48 ms 31776 KB Output is correct
8 Correct 264 ms 99940 KB Output is correct
9 Correct 322 ms 100052 KB Output is correct
10 Correct 45 ms 31872 KB Output is correct
11 Correct 392 ms 114212 KB Output is correct
12 Correct 354 ms 114124 KB Output is correct
13 Correct 285 ms 114576 KB Output is correct
14 Correct 50 ms 31852 KB Output is correct
15 Correct 265 ms 97076 KB Output is correct
16 Correct 316 ms 96188 KB Output is correct
17 Correct 398 ms 97812 KB Output is correct
18 Correct 422 ms 97668 KB Output is correct
19 Correct 490 ms 103204 KB Output is correct
20 Correct 486 ms 102108 KB Output is correct
21 Correct 335 ms 98832 KB Output is correct
22 Correct 290 ms 98728 KB Output is correct
23 Correct 403 ms 98376 KB Output is correct
24 Correct 444 ms 98136 KB Output is correct
25 Correct 488 ms 104576 KB Output is correct
26 Correct 447 ms 95832 KB Output is correct
27 Correct 420 ms 95416 KB Output is correct
# Verdict Execution time Memory Grader output
1 Correct 53 ms 31760 KB Output is correct
2 Correct 66 ms 34036 KB Output is correct
3 Correct 59 ms 34060 KB Output is correct
4 Correct 68 ms 34196 KB Output is correct
5 Correct 60 ms 34124 KB Output is correct
6 Correct 68 ms 33880 KB Output is correct
7 Correct 48 ms 31776 KB Output is correct
8 Correct 264 ms 99940 KB Output is correct
9 Correct 322 ms 100052 KB Output is correct
10 Correct 45 ms 31872 KB Output is correct
11 Correct 392 ms 114212 KB Output is correct
12 Correct 354 ms 114124 KB Output is correct
13 Correct 285 ms 114576 KB Output is correct
14 Correct 50 ms 31852 KB Output is correct
15 Correct 265 ms 97076 KB Output is correct
16 Correct 316 ms 96188 KB Output is correct
17 Correct 398 ms 97812 KB Output is correct
18 Correct 422 ms 97668 KB Output is correct
19 Correct 490 ms 103204 KB Output is correct
20 Correct 486 ms 102108 KB Output is correct
21 Correct 335 ms 98832 KB Output is correct
22 Correct 290 ms 98728 KB Output is correct
23 Correct 403 ms 98376 KB Output is correct
24 Correct 444 ms 98136 KB Output is correct
25 Correct 488 ms 104576 KB Output is correct
26 Correct 447 ms 95832 KB Output is correct
27 Correct 420 ms 95416 KB Output is correct
28 Incorrect 51 ms 31788 KB Extra information in the output file
29 Halted 0 ms 0 KB -