P2501 [HAOI2006]数字序列

题目描述

现在我们有一个长度为n的整数序列A。但是它太不好看了,于是我们希望把它变成一个单调严格上升的序列。但是不希望改变过多的数,也不希望改变的幅度太大。

输入输出格式

输入格式:

第一行包含一个数n,接下来n个整数按顺序描述每一项的键值。

输出格式:

第一行一个整数表示最少需要改变多少个数。

第二行一个整数,表示在改变的数最少的情况下,每个数改变的绝对值之和的最小值。

说明

90%的数据n<=6000。

100%的数据n<=35000。

保证所有数列是随机的。


“数据随机”==乱搞 啊哈

陷入了笛卡尔树的坑里

看了题解,大家一致认为第一问灰常简单,第二问灰常毒瘤

我:

好吧,第一问其实有思想的,发现直接求要改变的死活不好弄,不妨使用补集转换的思想,求最多不改变的数字

设\(dp_i\)代表以\(i\)为末尾的数字不改变时的最大不改变数字

转移有:

\(dp_i=max_{a_i-a_j \ge i-j} dp_j +1\)

复杂度是\(O(N^2)\)的

我们发现,其实我们是在最大化转移次数

如果把转移条件移项\(a_i-i \ge a_j-j\)

设\(b_i=a_i-i\),问题就转换成了求\(LIS\),可以\(O(nlogn)\)求解

第二问 有点微妙 实质上是一个跑不满的\(O(N^3)\)做法,上界极其宽松(当然要写的好才行)

把\(a\)变得单调上升,等价与把\(b\)变的单调不降,花费是等价的

设\(f_i\)为把前\(i\)项合法的最小花费

转移有:

\(f_i=min_{dp_i==dp_j+1} f_j+cost_{i,j}\)

先不考虑如何计算花费,考虑卡枚举前一维的常数

很显然前\(i\)项是要跑满的,从哪里转移我们建一个链表就表示转移集合

考虑如何计算费用

发现如果可以转移,那所有的在\(b_i\)和\(b_i\)之间的\(b\)没有值是夹在它们中间的。

它们一定会往两端进行靠拢,可以证明(没看懂原证明),存在一个\(k\),使\(b_i\)$b_k$都为$b_i$,使$b_k+1$\(b_j\)都为\(b_j\)

所有我们只需要枚举中间的这个\(k\)就行啦

代码细节还是很多的,没给值域还是很坑的


Code:

#include <cstdio>
#include <cstring>
#include <algorithm>
#include <vector>
#define ll long long
ll min(ll x,ll y){return x<y?x:y;}
ll abs(ll x){return x>0?x:-x;}
const ll N=35002;
ll n,a[N],b[N],g[N],k;
std::vector <ll > dx[N];ll dp[N],s1[N],s2[N];
int main()
{
scanf("%lld",&n);dp[0]=-0x3f3f3f3f,b[n+1]=-dp[0],b[0]=dp[0];
for(ll i=1;i<=n;i++)
scanf("%lld",a+i),b[i]=a[i]-i;
for(ll i=1;i<=n;i++)
{
if(b[i]>=dp[k]) dp[++k]=b[i],g[i]=k;
else
{
g[i]=std::upper_bound(dp+1,dp+1+k,b[i])-dp;
dp[g[i]]=b[i];
}
}
printf("%lld\n",n-k);g[++n]=k+1;
for(ll i=0;i<=n;i++) dx[g[i]].push_back(i);
memset(dp,0x3f,sizeof(dp));
dp[0]=0;
for(ll i=1;i<=n;i++)
{
for(ll j=0;dx[g[i]-1][j]<i&&j<dx[g[i]-1].size();j++)
{
ll to=dx[g[i]-1][j];
if(b[i]<b[to]) continue;
for(ll l=to;l<=i;l++) s1[l]=abs((ll)(b[l]-b[to])),s2[l]=abs((ll)(b[l]-b[i]));
for(ll l=to+1;l<=i;l++) s1[l]+=s1[l-1],s2[l]+=s2[l-1];
for(ll l=to;l<=i;l++)
dp[i]=min(s1[l]-s1[to]+s2[i]-s2[l]+dp[to],dp[i]);
}
}
printf("%lld\n",dp[n]);
return 0;
}

洛谷 P2501 [HAOI2006]数字序列 解题报告的更多相关文章

  1. 洛谷 P4093 [HEOI2016/TJOI2016]序列 解题报告

    P4093 [HEOI2016/TJOI2016]序列 题目描述 佳媛姐姐过生日的时候,她的小伙伴从某宝上买了一个有趣的玩具送给他.玩具上有一个数列,数列中某些项的值可能会变化,但同一个时刻最多只有一 ...

  2. 洛谷 P2659 美丽的序列 解题报告

    P2659 美丽的序列 题目背景 GD是一个热衷于寻求美好事物的人,一天他拿到了一个美丽的序列. 题目描述 为了研究这个序列的美丽程度,GD定义了一个序列的"美丽度"和" ...

  3. 2021.12.06 P2501 [HAOI2006]数字序列(动态规划+LIS)

    2021.12.06 P2501 [HAOI2006]数字序列(动态规划+LIS) https://www.luogu.com.cn/problem/P2501 题意: 现在我们有一个长度为 n 的整 ...

  4. 洛谷_Cx的故事_解题报告_第四题70

    1.并查集求最小生成树 Code: #include <stdio.h> #include <stdlib.h>   struct node {     long x,y,c; ...

  5. 洛谷 P2317 [HNOI2005]星际贸易 解题报告

    P2317 [HNOI2005]星际贸易 题目描述 输入输出格式 输入格式: 输出格式: 如果可以找到这样的方案,那么输出文件output.txt中包含两个整数X和Y.X表示贸易额,Y表示净利润并且两 ...

  6. 洛谷 P3802 小魔女帕琪 解题报告

    P3802 小魔女帕琪 题目背景 从前有一个聪明的小魔女帕琪,兴趣是狩猎吸血鬼. 帕琪能熟练使用七种属性(金.木.水.火.土.日.月)的魔法,除了能使用这么多种属性魔法外,她还能将两种以上属性组合,从 ...

  7. 洛谷 P2606 [ZJOI2010]排列计数 解题报告

    P2606 [ZJOI2010]排列计数 题目描述 称一个\(1,2,...,N\)的排列\(P_1,P_2...,P_n\)是\(Magic\)的,当且仅当对所以的\(2<=i<=N\) ...

  8. 洛谷1303 A*B Problem 解题报告

    洛谷1303 A*B Problem 本题地址:http://www.luogu.org/problem/show?pid=1303 题目描述 求两数的积. 输入输出格式 输入格式: 两个数 输出格式 ...

  9. 洛谷 P1379 八数码难题 解题报告

    P1379 八数码难题 题目描述 在3×3的棋盘上,摆有八个棋子,每个棋子上标有1至8的某一数字.棋盘中留有一个空格,空格用0来表示.空格周围的棋子可以移到空格中.要求解的问题是:给出一种初始布局(初 ...

随机推荐

  1. Java源码解析——集合框架(四)——LinkedListLinkedList原码分析

    LinkedList源码分析 LinkedList也和ArrayList一样实现了List接口,但是它执行插入和删除操作时比ArrayList更加高效,因为它是基于链表的.基于链表也决定了它在随机访问 ...

  2. php成绩排序

    $arr = ['12','12','23']; $arr = $arr; $arr1=$arr; rsort($arr1); $c=[]; foreach ( $arr as $k=>$v){ ...

  3. python循环,函数

    平常的网页会转换成ascll码,在转编译成十六进制a='http://www.mywebsit.com/?query=python&count=20'print(a)b=a.replace(' ...

  4. web学习第二天

    今天是学习web的第二天,早上用css3做了个会动的小熊,border-radius为圆的半径, .smallxiong {    width: 400px;    height: 400px;    ...

  5. 解决如下出错:DeprecationWarning: Passing 1d arrays as data is deprecated in 0.17 and willraise ValueError in 0.19.

    背景:在Spyder中写几行脚本,目的是应用sklearn自带的svm(支持向量机)算法,来对其自带的digits(手写体数字)数据集进行分类,过程包括训练阶段和预测阶段.将手写体数字数据的特征数据d ...

  6. C语言实例解析精粹学习笔记——34(用“结构”统计学生成绩)

    实例34: 设学生信息包括学号.姓名和五门功课的成绩,要求编写输入输出学生信息的函数.在输入学生信息后,以学生成绩的总分从高到低顺序输出学生信息. 思路: 程序引入一个结构数组依次存储输入的学生信息, ...

  7. vue---day01

    1.let和const var 全局作用域和函数作用域 存在变量提升 其实是个bug 可以重复声明 let 块级作用域 不存在变量提升 不能重复声明 const 常量 和let一样还有另外两个 定义的 ...

  8. R语言学习笔记(四):apply,sapply,lapply,tapply,vapply以及mapply的用法

    apply() apply(m,dimcode,f,fargs) m 是一个矩阵. dimcode是维度编号,取1则为对行应用函数,取2则为对列运用函数. f是函数 fargs是f的可选参数集 > ...

  9. HBase 伪分布式环境搭建及基础命令使用

    一.前提条件: (1)文件存储在HDFS文件系统之上.因此必须启动hadoop服务.(namenode,datanode,resourcemanager,nodemanager,historyserv ...

  10. Spring + MySQL + Mybatis + Redis【二级缓存】

    一.Redis环境 Redis 官网 :http://redis.io/ windows下载:https://github.com/dmajkic/redis/downloads 1.文件解压缩 2. ...