义乌集训Day 3 T3

题目链接

先是想到直接暴力贪心分段,从l到r一个个枚举,如果<=k就不分

这样的时间复杂度是
O ( m n ) O(mn) O(mn)期望得分30pts

	while(m--)
    	{
    		ll r,l;l=read();r=read();
    		ll ans=1;
    		bool pd=0;
    		ll z=l;
    		for(int i=l;i<=r;i++)
    		{
    			if(a[i]>k){pd=1;break;}
    			if(sum[i]-sum[z-1]>k)ans++,z=i;
			}
			if(pd)printf("Chtholly\n");
			else printf("%d\n",ans);
		}

在看数据表可以看到,当a[i]=1的数据有两个,则ans=(r-l+1)/k

期望得分50分

	while(m--)
    	{
    		ll r,l;l=read();r=read();
    	
    		ll kk=r-l+1;
			 if(kk%k==0) printf("%d\n",kk/k);
			else printf("%d\n",kk/k+1);
		}	

100pts

因为是在一个个枚举的时候超时的,所以我们可以考虑能不能跳跃式地去找,这样就不会超时了。因此我们可以想到倍增

f [ i ] [ j ] 表 示 第 j 个 点 跳 1 < < i 此 可 以 跳 到 哪 里 f[i][j]表示 第 j 个点 跳 1<<i 此可以跳到哪里 f[i][j]j1<<i

倍增的转移就是 f [ i ] [ j ] = f [ i − 1 ] [ m i n ( n , f [ i − 1 ] [ j ] ) ] ; f[i][j]=f[i-1][min(n,f[i-1][j])]; f[i][j]=f[i1][min(n,f[i1][j])];

	 while(m--)
	 {
	 	int ans=0;
	 	int l,r;l=read();r=read();
	 	if(sum[r]-sum[l-1]){puts("Chtholly");continue;}
	 	for(int i=24;i>=0;i--)//倍增地去寻找
	 	if(f[i][l]<=r)ans+=1<<i,l=f[i][l];
	 	printf("%d\n",ans+1);
	 }
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值