嘘~ 正在从服务器偷取页面 . . .

洛谷P4552 [Poetize6] IncDec Sequence 题解


洛谷P4552 [Poetize6] IncDec Sequence 题解

题目链接:P4552 [Poetize6] IncDec Sequence

题意

给定一个长度为 \(n\) 的数列 \({a_1,a_2,\cdots,a_n}\),每次可以选择一个区间\([l,r]\),使这个区间内的数都加 \(1\) 或者都减 \(1\)

请问至少需要多少次操作才能使数列中的所有数都一样,并求出在保证最少次数的前提下,最终得到的数列有多少种。

对于 \(100\%\) 的数据,\(n\le 100000, 0 \le a_i \le 2^{31}\)

这道题思路比较有趣,代码很简单但是相对来说不好想

本文比较长,建议耐心阅读(当然也可以直接 ⌘+w 或者 ctrl+w

差分,常用于 \(O(1)\) 区间加减,全局询问

对于这种看上去也不是用数据结构做的题目,

考虑差分。差分数组 \(b_i\) 的定义为 \(b_i = a_i-a_{i-1}\)

容易发现 \(a_i = \sum_{1 \le j \le i}b_i\) ,值得注意的是, \(a_1 = b_1\)

对于区间 \([l,r]\)\(1\) 的修改,只要把 \(b_l\) 加上 \(1\)\(b_{r+1}\) 减去 \(1\) 就可以了

然后问题就转化为了将 \(b_2,b_3,\dots,b_n\) 都变成 \(0\) 的最小花费

观察差分的性质,其实每次修改就是在搬运一个 \(1\)

也就是把它从 \(b_l\) 搬到 \(b_{r+1}\) ,或者反过来搬

对于每个合法的修改,一定可以完成这样的操作

可以发现当 \(r=n\) 时会出现从外面搬过来或者搬到外面去的情况

先不急,我们先考虑 \(r<n\)

显然我们可以把所有的 \(b_i<0\)\(b_j >0\) 配对( \(2 \le i \le j \le n\) ),然后相互抵消

可以发现这样配对消去的最小花费为 \(\min(p,q)\)

其中 \(p= \sum_{1 \le i \le n} [b_i<0],~q= \sum_{1 \le i \le n} [b_i>0]\)

这样配对也会出现最后消不完的情况,

这个时候我们就可以把它们与 \(n+1\) 配对,或者 \(b_1\)

这样的答案是 \(\operatorname{abs}(p-q)\)

则最后的答案就是 \(\min(p,q)+\operatorname{abs}(p-q)=\max(p,q)\)

再看第二问,其实很简单

看我们的最后一步,如果和 \(b_1\) 配对 \(k\) 次,最后的 \(a_i\) 就会变成 \(b_1+k\)

所以方案数就是 \(\operatorname{abs}(p-q)+1\) (不与 \(b_1\) 配对也是一种情况)

然后就好了,时间复杂度 \(O(n)\)

代码:

#include <iostream>
#include <string>
#include <vector>
#include <algorithm>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <cmath>
#include <iomanip>
using namespace std;
#define int long long
#define INF 0x3f3f3f3f3f3f3f3f
#define N (int)(1e5+15)

int n,p,q,a[N];
signed main()
{
    ios::sync_with_stdio(0);
    cin.tie(0);cout.tie(0);
    // freopen("check.in","r",stdin);
    // freopen("check.out","w",stdout);
    cin >> n;
    for(int i=1; i<=n; i++)
        cin >> a[i];
    for(int i=2; i<=n; i++)
    {
        int c=a[i]-a[i-1];
        c>0?p+=c:q-=c;
    }
    cout << max(p,q) << '\n' << abs(p-q)+1 << '\n';
    return 0;
}

文章作者: q779
版权声明: 本博客所有文章除特别声明外,均采用 CC BY-NC-ND 4.0 许可协议。转载请注明来源 q779 !
评论
  目录