zoukankan      html  css  js  c++  java
  • CF1039D-You Are Given a Tree【根号分治,贪心】

    正题

    题目链接:https://www.luogu.com.cn/problem/CF1039D


    题目大意

    给出(n)个点的一棵树,然后对于(kin[1,n])求每次使用一条长度为(k)的链覆盖树并且不能重复覆盖点时最大覆盖条数。

    (1leq nleq 10^5)


    解题思路

    先考虑暴力怎么做,因为每条链的价值都是一,显然的一种贪心思想是能合并的就合并(没有让出一条链给另一条链腾空间的必要)。

    这样的复杂度是(O(n))的,但是对于每个都要求所以需要优化。

    之后考虑上根号分治,对于一个(k)的答案显然不会超过(frac{n}{k}),所以可以当(kleq sqrt n)的时候暴力做,然后由于答案递增,大于(sqrt n)(k)答案的取值不会超过(sqrt n),每次二分断点即可。时间复杂度(O(nsqrt nlog n))

    其实发现这样还是不够快,可以找到一个更好的阈值,设为(T),那么前面的复杂度就是(T),后面的复杂度就是(frac{n}{T}log n),用平衡规划的思想当(T=frac{n}{T}log n)时最快,也就是(T=sqrt{nlog n})时最快了。


    code

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<cmath>
    using namespace std;
    const int N=1e5+10;
    struct node{
    	int to,next;
    }a[N<<1];
    int n,tot,cnt,dfn[N],ls[N],fa[N],f[N];
    void addl(int x,int y){
    	a[++tot].to=y;
    	a[tot].next=ls[x];
    	ls[x]=tot;return;
    }
    void dfs(int x){
    	dfn[++cnt]=x;
    	for(int i=ls[x];i;i=a[i].next){
    		int y=a[i].to;
    		if(y==fa[x])continue;
    		fa[y]=x;dfs(y);
    	}
    	return;
    }
    int solve(int k){
    	if(k==1)return n;
    	int ans=0;
    	for(int i=1;i<=n;i++)f[i]=1;
    	for(int i=n;i>=1;i--){
    		int x=dfn[i];
    		if(f[x]&&f[fa[x]]){
    			if(f[x]+f[fa[x]]>=k)
    				ans++,f[fa[x]]=0;
    			else f[fa[x]]=max(f[fa[x]],f[x]+1);
    		}
    	}
    	return ans;
    }
    int main()
    {
    	scanf("%d",&n);
    	for(int i=1;i<n;i++){
    		int x,y;
    		scanf("%d%d",&x,&y);
    		addl(x,y);addl(y,x);
    	}
    	dfs(1);
    	int T=sqrt((double)n*(log(n)/log(2))),last,z=T+1;
    	for(int i=1;i<=T;i++)printf("%d
    ",last=solve(i));
    	while(z<=n){
    		int l=z+1,r=n,k=solve(z);
    		while(l<=r){
    			int mid=(l+r)>>1;
    			if(solve(mid)<k)r=mid-1;
    			else l=mid+1;
    		}
    		for(int i=z;i<=r;i++)
    			printf("%d
    ",k);
    		z=r+1;
    	}
    	return 0;
    }
    
  • 相关阅读:
    HDU 5744
    HDU 5815
    POJ 1269
    HDU 5742
    HDU 4609
    fzu 1150 Farmer Bill's Problem
    fzu 1002 HangOver
    fzu 1001 Duplicate Pair
    fzu 1150 Farmer Bill's Problem
    fzu 1182 Argus 优先队列
  • 原文地址:https://www.cnblogs.com/QuantAsk/p/15343702.html
Copyright © 2011-2022 走看看