【蓝桥杯每日一题】3.9 截断数组

原题链接:5480. 截断数组 - AcWing题库

主要思想:贪心+双指针

注意点:

  • 每次操作都需要一定成本,具体来说,将数组从 a i a_i ai a i + 1 a_{i+1} ai+1 之间截断,所需成本为 ∣ a i − a i + 1 ∣ |a_i - a_{i+1}| aiai+1
  • 所有进行的截断操作的总成本不得超过 B B B
  • 所有截断得到的子数组都必须也是平衡数组
  • 只是截断a[]数组,不再对a[]数组的子数组再进行操作

思考:

  • 通过一次遍历计算并存储所有潜在的截断成本到数组 k [ ] k[] k[]中。利用了平衡数组的性质:只有当遍历到的位置使得前面的子数组为平衡数组时,才记录成本
  • 由于是要得出最大的截断数,所以从最小的截断成本开始,因此要对数组 k [ ] k[] k[]进行排序
  • 遍历数组 k [ ] k[] k[],尝试执行每个符合题目要求的操作,同时保持最大成本不超过 B B B,每有一个成功的操作,计数器 M a x C u t MaxCut MaxCut ++;

AC代码:

#include <bits/stdc++.h>
using namespace std;
int n, B;
int a[1010];
int cost[1010];
int cnt=0;
int MaxCut=0;
int main() {

    scanf("%d%d",&n,&B);

	for(int i=1;i<=n;i++){
		scanf("%d",&a[i]);
	}
	
	for(int i=1,ji=0,ou=0;i<n;i++) //由于是子数组,所以少一
	{
		if(a[i]%2==0) ou++;
		else ji++;
		if(ji==ou) cost[cnt++]=abs(a[i]-a[i+1]);
	}
	sort(cost,cost+cnt);
	
	for(int i=0;i<cnt;i++)
	{
		if(cost[i]<=B)
		{
			B-=cost[i];
			MaxCut++;
		}
	}
	printf("%d",MaxCut);
    return 0;
}
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值