洛谷 P4552 [Poetize6] IncDec Sequence (差分)

题目链接

题目思路

显然在一个区间内做加法和减法要使用差分,然而我没想到。。。
肯定是要使得差分数组[2,n]全部为0,而dif[1]有多少个取值,则决定了有多少个可能取值。

很明显的,在我们求出的差分数组中,有正数也有负数,要消除这些数,使得它们全部归零,我们有以下3种可行的操作:

1:选取一个正数(X)和一个负数(Y),使正数减1,负数加1,这样经过N次操作,我们一定可以以最少的代价将绝对值较小的一方归零,代价为abs(min(X,Y))

2:选取一个正数(X),使其与 S[1] 配对或s[n+1],这样,我们经过N次操作,一定可以将它归零,代价为:abs(X)

3:选取一个负数(Y),使其与 S[n+1] 配对或s[n+1],这样,我们经过N次操作,一定可以将它归零,代价为:abs(Y)

经过上述分析,我们就能够推导出本题的解题公式:
ans=abs(min(X,Y))+abs(X-Y)=abs(max(X,Y))
需要注意的是这里的X,Y是差分数组中所有正数的和与所有负数的和的绝对值
最后我们还要求能构成几组解,这很容易可以推出:
剩下的abs(X-Y)次操作可以配对给d[n+1]或者d[1]所以有abs(x-y)+1种答案

代码

#include<cstdio>
#include<cmath>
#include<algorithm>
using namespace std;
typedef long long ll;
const int maxn=1e5+5;
ll n,a[maxn],dif[maxn],zhen,fu;
int main(){
    scanf("%lld",&n);
    for(int i=1;i<=n;i++){
        scanf("%lld",&a[i]);
    }
    for(int i=2;i<=n;i++){
        dif[i]=a[i]-a[i-1];
        if(dif[i]>0){
            zhen+=dif[i];
        }else{
            fu-=dif[i];
        }
    }
    printf("%lld\n%lld\n",max(zhen,fu),abs(zhen-fu)+1);
    return 0;
}

参考链接:https://www.luogu.com.cn/blog/TheShadow/p4552-poetize6-incdec-sequence-you-qu-di-ci-fen-ti-xie

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值