【洛谷P4552】IncDec Sequence

这是一道经典的差分题。

思路大概是这样的:

对于输入的序列a(假定长度为n)

我们求出他的差分序列sum

那么题目就转化成了用最少的步数使得差分序列sum的2~n项都为0

那么就有以下的几种决策:

  1. 第i位+1,第j位-1
  2. 第1位+1,第j位-1
  3. 第i位+1,第n+1位-1

显然,在sumi和sumj一正一负的前提下,我们应该尽可能多的使用第一种,这样才能使答案最优。

统计sum数组当中正整数的和为p,负整数的和为q,那么能用min(q,p)次决策1。剩下的使用|p-q|次决策2,3。

所以答案为max(q,p),能产生|p-q|+1种情况。

 1 #include <iostream>
 2 #include <cstdio>
 3 typedef long long ll;
 4 inline ll read() {
 5     ll ret=0,f=1;
 6     char c=getchar();
 7     while(c<'0'||c>'9') {if(c=='-') f=-1;c=getchar();}
 8     while(c<='9'&&c>='0') ret=ret*10+c-'0',c=getchar();
 9     return ret*f;
10 }
11 using namespace std;
12 ll a[100010],sum[100010],n,zheng,fu;
13 ll abs(ll x) {
14     return x>0?x:-x;
15 }
16 int main() {
17     n=read();
18     for(int i=1;i<=n;i++) {
19         a[i]=read();
20         sum[i]=a[i]-a[i-1];
21     }
22     for(int i=2;i<=n;i++) {
23         if(sum[i]>0) zheng+=sum[i];
24         else fu+=(0-sum[i]);
25     }
26     printf("%lld\n%lld",max(zheng,fu),abs(zheng-fu)+1);
27     return 0;
28 }
AC Code

猜你喜欢

转载自www.cnblogs.com/shl-blog/p/10541917.html