专栏文章
[CF2167F] Tree, TREE!!! 题解
CF2167F题解参与者 1已保存评论 0
文章操作
快速查看文章及其快照的属性,并进行相关操作。
- 当前评论
- 0 条
- 当前快照
- 1 份
- 快照标识符
- @min55ylb
- 此快照首次捕获于
- 2025/12/01 20:44 3 个月前
- 此快照最后确认于
- 2025/12/01 20:44 3 个月前
先考虑 在 内需要满足的条件,首先在选择 LCA 时不能选在 子树外的点,否则 LCA 只能为 的祖先。接下来可以强制钦定 被选择,那么只要接下来选的点都在 子树内,LCA 就必然是 。于是需要满足 个点能在 子树内选完,即 。
考察 在根变化时会如何变化。令根为 ,得到此时 子树大小 。
- 若 在 的儿子 的子树内,则 ,一共有 个这样的 ;
- 若 在 的子树外,则 ,一共有 个这样的 ;
- 若 ,则 。
于是可以轻松求出 对答案的贡献。
时间复杂度线性。
code
CPP#include<bits/stdc++.h>
#define pb emplace_back
#define mp make_pair
#define pob pop_back
using namespace std;
typedef long long ll;
const ll maxn=200007,ee=1e18;
ll n,k,siz[maxn],ans;
vector<ll> edge[maxn];
void dfs(ll u,ll fa){
siz[u]=1;
for(auto v:edge[u]){
if(v==fa) continue;
dfs(v,u),siz[u]+=siz[v];
ans+=siz[v]*(n-siz[v]>=k);
}
ans+=(n-siz[u])*(siz[u]>=k);
}
int main(void){
//freopen("data.in","r",stdin);
//freopen("data.out","w",stdout);
ios::sync_with_stdio(0),cin.tie(0);
ll T=1; cin>>T;
for(;T--;){
for(ll i=1;i<=n;i++) edge[i].clear();
cin>>n>>k,ans=n;
for(ll i=1,u,v;i<n;i++){
cin>>u>>v;
edge[u].pb(v),edge[v].pb(u);
}
dfs(1,0);
cout<<ans<<"\n";
}
return 0;
}
相关推荐
评论
共 0 条评论,欢迎与作者交流。
正在加载评论...