CodeForces - 246E Blood Cousins Return(树上启发式合并)
生活随笔
收集整理的這篇文章主要介紹了
CodeForces - 246E Blood Cousins Return(树上启发式合并)
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
題目鏈接:點擊查看
題目大意:給出一棵家譜樹,定義從 u 點向上走 k 步到達的節點為 u 的 k-ancestor,每個節點有名字,名字不唯一。多次查詢,給出 u 和 k,問以 u 為根節點的子樹下有多少個深度為 dep[u] + k 的節點(dep[u] 為節點 u 的深度)。
題目分析:有了之前那道題目的鋪墊后:CodeForces - 208E Blood Cousins,這道題目機會就是來白給的,與前一道題目不同的是,這個題目是需要統計以u為根節點的子樹中,相對深度為k的子結點中,有多少種名字,注意這里,是多少種而不是多少個,既然是需要去重,那么直接上set和string配合使用就好了,將前一個題目中的cnt替換為set就大功告成了
有個細節需要注意一下,題目中給出的u和k,可能會無解,我們有兩種方法,一種是在dfs維護深度時順便維護一下max_deep,用來限制范圍,超過范圍的直接將答案置零即可,或者是一開始就將set數組開大點,大上個兩倍就夠了
代碼:
#include<iostream> #include<cstdio> #include<string> #include<ctime> #include<cstring> #include<algorithm> #include<stack> #include<queue> #include<map> #include<set> #include<sstream> #include<unordered_map> using namespace std;typedef long long LL;const int inf=0x3f3f3f3f;const int N=1e5+100;string name[N];int deep[N],son[N],num[N],ans[N],limit,max_deep;bool vis[N];set<string>st[N<<1];vector<int>node[N];vector<pair<int,int>>Q[N];//<id,deep>void dfs_son(int u,int dep) {max_deep=max(dep,max_deep);son[u]=-1;num[u]=1;deep[u]=dep;for(auto v:node[u]){dfs_son(v,dep+1);num[u]+=num[v];if(son[u]==-1||num[son[u]]<num[v])son[u]=v;} }void cal(int u,int val) {if(val==1)st[deep[u]].insert(name[u]);elsest[deep[u]].erase(name[u]);for(auto v:node[u]){if(vis[v])continue;cal(v,val);} }void dfs(int u,int keep) {for(auto v:node[u]){if(v==son[u])continue;dfs(v,0);}if(son[u]!=-1){dfs(son[u],1);vis[son[u]]=true;}cal(u,1);for(auto i:Q[u]){int id=i.first;int d=i.second;ans[id]=st[d].size();}if(son[u]!=-1)vis[son[u]]=false;if(!keep)cal(u,-1); }int main() { // freopen("input.txt","r",stdin); // ios::sync_with_stdio(false);int n,m;scanf("%d",&n);limit=log2(n)+1;for(int i=1;i<=n;i++){cin>>name[i];int fa;scanf("%d",&fa);node[fa].push_back(i);}dfs_son(0,0);scanf("%d",&m);for(int i=1;i<=m;i++){int u,d;scanf("%d%d",&u,&d);Q[u].push_back(make_pair(i,deep[u]+d));}dfs(0,1);for(int i=1;i<=m;i++)printf("%d\n",ans[i]);return 0; }?
總結
以上是生活随笔為你收集整理的CodeForces - 246E Blood Cousins Return(树上启发式合并)的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: CodeForces - 570D Tr
- 下一篇: CodeForces - 1288C T