/*
Ben Watson
Quang Minh MasterDDDDD
*/
#include <bits/stdc++.h>
using namespace std;
#define ll long long
const string name = "test";
void solve();
signed main()
{
if (fopen((name + ".inp").c_str(), "r"))
{
freopen((name + ".inp").c_str(), "r", stdin);
freopen((name + ".out").c_str(), "w", stdout);
}
ios_base::sync_with_stdio(0); cin.tie(0); cout.tie(0);
solve();
return 0;
}
// main program
const int oo = 0x3f3f3f3f;
const int maxn = 1e5 + 1;
struct FenwickTree
{
vector<int> bits;
int n;
FenwickTree(int n) : n(n) { bits.resize(n + 1, 0); }
void update(int pos, int val)
{
for (; pos <= n; pos += (pos & (-pos)))
bits[pos] += val;
}
int query(int pos)
{
int res = 0;
for (; pos > 0; pos -= (pos & (-pos)))
res += bits[pos];
return res;
}
int query(int l, int r) { return query(r) - query(l - 1); }
};
vector<int> adj[maxn], queries[maxn];
int c[maxn], ans[maxn], L[maxn];
FenwickTree bit(maxn);
int n, m, q;
// tree processing
int pos[maxn], tp[maxn], sz[maxn], par[maxn], d[maxn];
void DFS(int u, int p = -1)
{
sz[u] = 1;
for (int v : adj[u])
{
if (v == p)
continue;
par[v] = u;
d[v] = d[u] + 1;
DFS(v, u);
sz[u] += sz[v];
}
}
int timeDFS = 0;
void DFS_HLD(int u, int top)
{
pos[u] = ++timeDFS;
tp[u] = top;
int nxt = -1;
for (int v : adj[u])
if (v != par[u] && (nxt == -1 || sz[v] > sz[nxt]))
nxt = v;
if (nxt != -1)
DFS_HLD(nxt, top);
for (int v : adj[u])
if (v != par[u] && v != nxt)
DFS_HLD(v, v);
}
// handle queries
int Left[maxn], X[maxn];
set<int> se;
void update(int l, int r, int x)
{
int st = *(se.lower_bound(r));
while (st > 0)
{
int u = Left[st], v = st;
st = u - 1;
if (v < l) break;
if (r < u) continue;
int le = max(u, l), ri = min(v, r), val = X[v];
if (u < l)
{
se.insert(l - 1);
Left[l - 1] = u;
X[l - 1] = val;
Left[ri] = l;
X[ri] = x;
}
if (r < v)
{
se.insert(r);
Left[v] = r + 1;
X[v] = val;
Left[r] = le;
X[r] = x;
}
bit.update(val + 1, -(ri - le + 1));
X[ri] = x;
}
bit.update(x + 1, r - l + 1);
}
void update_path(int u, int v, int x)
{
while (tp[u] != tp[v])
{
if (d[tp[u]] < d[tp[v]])
swap(u, v);
update(pos[tp[u]], pos[u], x);
u = par[tp[u]];
}
if (d[u] > d[v])
swap(u, v);
update(pos[u], pos[v], x);
}
void solve()
{
cin >> n >> m >> q;
for (int i = 1; i < n; i++)
{
int u, v; cin >> u >> v;
adj[u].push_back(v);
adj[v].push_back(u);
}
for (int i = 1; i <= m; i++)
cin >> c[i];
DFS(1);
DFS_HLD(1, 1);
bit.update(1, n);
se.insert(n);
Left[n] = 1;
for (int i = 1; i <= q; i++)
{
int l, r; cin >> l >> r;
L[i] = l;
queries[r].push_back(i);
}
for (int i = 1; i <= m; i++)
{
if (i != 1)
update_path(c[i - 1], c[i], i - 1);
update_path(c[i], c[i], i);
for (int idx : queries[i])
ans[idx] = bit.query(L[idx] + 1, m + 1);
}
for (int i = 1; i <= q; i++)
cout << ans[i] << '\n';
}
Compilation message (stderr)
tourism.cpp: In function 'int main()':
tourism.cpp:19:16: warning: ignoring return value of 'FILE* freopen(const char*, const char*, FILE*)' declared with attribute 'warn_unused_result' [-Wunused-result]
19 | freopen((name + ".inp").c_str(), "r", stdin);
| ~~~~~~~^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
tourism.cpp:20:16: warning: ignoring return value of 'FILE* freopen(const char*, const char*, FILE*)' declared with attribute 'warn_unused_result' [-Wunused-result]
20 | freopen((name + ".out").c_str(), "w", stdout);
| ~~~~~~~^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |