제출 #1307582

#제출 시각아이디문제언어결과실행 시간메모리
1307582buzdiRegions (IOI09_regions)C++17
100 / 100
2988 ms49416 KiB
#include <bits/stdc++.h> #define ll long long using namespace std; const int NMAX = 2e5; const int RMAX = 25000; const int BLOCK = 500; int n, r, q, t; int reg[NMAX + 1]; int freq[RMAX + 1]; int in[NMAX + 1], out[NMAX + 1]; int sp[NMAX + 1]; vector<int> g[NMAX + 1], in_reg[RMAX + 1], nodes_reg[RMAX + 1]; vector<int> calc[RMAX + 1]; void DFS2(int node, int r1, int dad = 0, int cnt = 0) { calc[r1][reg[node]] += cnt; for(int next_node : g[node]) { if(next_node != dad) { DFS2(next_node, r1, node, cnt + (reg[node] == r1)); } } } void precalc() { for(int i = 1; i <= r; i++) { if(freq[i] > BLOCK) { calc[i].resize(n + 1); DFS2(1, i); } } } void DFS1(int node, int dad = 0) { in[node] = ++t; in_reg[reg[node]].push_back(in[node]); for(int next_node : g[node]) { if(next_node != dad) { DFS1(next_node, node); } } out[node] = t; } int query_small(int r1, int r2) { int answer = 0; for(int node : nodes_reg[r1]) { auto itr = upper_bound(in_reg[r2].begin(), in_reg[r2].end(), out[node]); auto itl = lower_bound(in_reg[r2].begin(), in_reg[r2].end(), in[node]); answer += itr - itl; } return answer; } int query_big(int r1, int r2) { return calc[r1][r2]; } int main() { ios::sync_with_stdio(0); cin.tie(0); cout.tie(0); cin >> n >> r >> q; cin >> reg[1]; for(int i = 2; i <= n; i++) { int x; cin >> x >> reg[i]; g[x].push_back(i); g[i].push_back(x); } for(int i = 1; i <= n; i++) { nodes_reg[reg[i]].push_back(i); freq[reg[i]]++; } DFS1(1); precalc(); while(q--) { int r1, r2; cin >> r1 >> r2; if(freq[r1] <= BLOCK) { cout << query_small(r1, r2) << endl; } else { cout << query_big(r1, r2) << endl; } } return 0; }
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...