应要求写一下这个题的题解。

我的DP很奥(奇)妙(怪),不过跟标算还是殊途同归的(反正怎么做都行……)

先讲一下奥妙的性质吧。

首先,在最终序列中,每个数最多出现一段,并且,对于出现的数,每段数两两之间的相对位置相较原序列保持不变。

然后,你还可以发现,一个数可以延伸到最左的左端点、和最右的右端点,这些都是可以算出来的。

如果我们不考虑操作次数的限制,这个问题就变成了,按顺序给你一堆区间,让你在每个区间里选一小段,使选出来的区间不重叠地覆盖整个序列,并且区间之间的相对位置要按照给定的顺序。

下面考虑次数限制,可以发现,对于一个合法的目标序列(合法的意思就是符合前面的要求,对应到题目就是能够通过操作得到),最优的操作方案显然是按由小到大的顺序对每个数进行操作,并且对每个数之多操作1次。

进一步考虑,发现,对于一个数,我们不需要对它进行操作,当且仅当该数不在最终序列中出现,或者该数在最终序列中出现的位置恰好仅为该数在原序列中的位置。

换句话说,操作k次就是限制了,你的最终序列只能有k段数(如果一个数只在原序列出现的位置出现,那么就不算一段数,需要特判)

之后就是dp,令dp[k][i]表示现在已经有k段数,并且当前计算到原序列左起第i个数的段。

作者太懒了,反正是普及组DP,你们自己脑补好了,那个特判还是要想一想的(对于我这种老年选手)。

(我觉得我已经说得很详细了啊TaT)

(嘛...主要是好困想碎叫QuQ)

代码:

  1. #include <iostream>
  2. #include <cstdio>
  3. #include <cstring>
  4. #include <cmath>
  5. #include <cstdlib>
  6. #include <algorithm>
  7. #define ll long long
  8. #define N 505
  9. #define P 1000000007
  10.  
  11. using namespace std;
  12. inline int read(){
  13. int ret=0;char ch=getchar();
  14. while (ch<'0'||ch>'9') ch=getchar();
  15. while ('0'<=ch&&ch<='9'){
  16. ret=ret*10-48+ch;
  17. ch=getchar();
  18. }
  19. return ret;
  20. }
  21.  
  22. int kk;
  23. int n,a[N];
  24. int l[N],r[N];
  25. int dp[N][N],dlt[N];
  26.  
  27. int main(){
  28. n=read();kk=read();
  29. for (int i=1;i<=n;++i) a[i]=read();
  30. memset(dp,0,sizeof(dp));dp[0][0]=1;
  31. for (int i=1;i<=n;++i){
  32. int l,r;
  33. for (l=i;l>1&&a[l-1]<a[i];--l);
  34. for (r=i;r<n&&a[r+1]<a[i];++r);
  35. (dp[kk][i]+=dp[kk][i-1])%=P;
  36. for (int k=kk-1;k>=0;--k){
  37. dlt[l-1]=0;
  38. for (int j=l;j<=r;++j) dlt[j]=(dlt[j-1]+dp[k][j-1])%P;
  39. for (int j=l;j<=r;++j) (dp[k+1][j]+=dlt[j])%=P;
  40. (dp[k][i]+=dp[k][i-1])%=P;
  41. (dp[k+1][i]+=P-dp[k][i-1])%=P;
  42. }
  43. }
  44. int ans=0;
  45. for (int i=0;i<=kk;++i) (ans+=dp[i][n])%=P;
  46. printf("%d\n",ans);
  47. return 0;
  48. }

  

bzoj4621: Tc605的更多相关文章

  1. BZOJ4621 Tc605(动态规划)

    容易发现最终序列所有数字的相对顺序不变,一个数字可能的覆盖范围由两边第一个比它大的数决定,且若不考虑次数限制所有这样的序列都可以变换得到.对于一个序列,其需要的最少变换次数显然就是覆盖了别的位置的数的 ...

  2. 【BZOJ4621】Tc605 DP

    [BZOJ4621]Tc605 Description 最初你有一个长度为 N 的数字序列 A.为了方便起见,序列 A 是一个排列. 你可以操作最多 K 次.每一次操作你可以先选定一个 A 的一个子串 ...

  3. bzoj 4621 Tc605 思想+dp

    4621: Tc605 Time Limit: 15 Sec  Memory Limit: 128 MBSubmit: 328  Solved: 183[Submit][Status][Discuss ...

  4. bzoj 4621: Tc605 动态规划

    题解: 一道比较简单的题目 想着想着就把题目记错了..想成了可以把某段区间覆盖为其中一个数 其实是比较简单的 每个点的贡献一定是一个区间(就跟zjoi2018那题一样) 然后问题就变成了给你n个区间让 ...

  5. BZOJ 4621: Tc605

    Description 最初你有一个长度为 N 的数字序列 A.为了方便起见,序列 A 是一个排列. 你可以操作最多 K 次.每一次操作你可以先选定一个 A 的一个子串,然后将这个子串的数字全部变成原 ...

  6. bzoj AC倒序

    Search GO 说明:输入题号直接进入相应题目,如需搜索含数字的题目,请在关键词前加单引号 Problem ID Title Source AC Submit Y 1000 A+B Problem ...

随机推荐

  1. SpringMVC + Spring + MyBatis 整合 + Spring shrio + easyUI + 权限管理框架,带shrio session和shrio cache集群实现方案

    工作之余先来写了一个不算规范的简单架子 基于spring mvc + spring + mybatis + Spring shrio 基于redis的集群方案 系统权限部分,分成多个机构,其中每个机构 ...

  2. Android版本和API Level对应关系

    http://developer.android.com/guide/topics/manifest/uses-sdk-element.html Platform Version       API ...

  3. (八)Eclipse创建Maven项目运行mvn命令

    1.Eclipse创建Maven项目 使用Eclipse创建一个Maven项目非常的简单,选择菜单项File>New>Other(也可以在项目结构空白处右击鼠标键),在弹出的对话框中选择M ...

  4. Node.js 教程 04 - 模块系统

    前言: Node.js的模块系统类似于C/C++的文件引用,可以声明对象,也可以定义类 创建对象. 大家这么理解,就简单了. 定义: 为了让Node.js的文件可以相互调用,Node.js提供了一个简 ...

  5. Windows API 函数列表 附帮助手册

    所有Windows API函数列表,为了方便查询,也为了大家查找,所以整理一下贡献出来了. 帮助手册:700多个Windows API的函数手册 免费下载 API之网络函数 API之消息函数 API之 ...

  6. MS SQL巡检系列——检查外键字段是否缺少索引

    前言感想:一时兴起,突然想写一个关于MS SQL的巡检系列方面的文章,因为我觉得这方面的知识分享是有价值,也是非常有意义的.一方面,很多经验不足的人,对于巡检有点茫然,不知道要从哪些方面巡检,另外一方 ...

  7. 分布式一致性算法--Paxos

    Paxos算法是莱斯利·兰伯特(Leslie Lamport)1990年提出的一种基于消息传递的一致性算法.Paxos算法解决的问题是一个分布式系统如何就某个值(决议)达成一致.在工程实践意义上来说, ...

  8. Java 消息摘要 散列 MD5 SHA

    package xxx.common.util; import java.math.BigInteger; import java.security.MessageDigest; import jav ...

  9. Windows Server 2012 虚拟化实战:网络(二)

    关于Windows Server的虚拟化网络,前文描述了在操作系统层面上的出现的配置变化.其中的一些配置通过Windows Server提供的小工具即可实现,如网卡组的配置,而有些需要安装Window ...

  10. 异步方法的意义何在,Async和await以及Task的爱恨情仇,还有多线程那一家子。

    前两天刚感受了下泛型接口的in和out,昨天就开始感受神奇的异步方法Async/await,当然顺路也看了眼多线程那几个.其实多线程异步相关的类单个用法和理解都不算困难,但是异步方法Async/awa ...