CodeChef MOU2H

来源:互联网 发布:win10系统优化软件 编辑:程序博客网 时间:2024/06/11 09:37

这个题有中文版,就直接把链接放上吧:传送门


大致题意是给出一个长度为 n 的序列,相邻的数之间作差,形成一个新的长度为 n-1 的差序列;

现在要在这 n-1 个数中取出至少一个组成一个新的序列,问一共可以组成多少种不同的序列(mod 1e9+9)。


一个典型的 dp 题,dp[i] 表示前 i 个数的答案,初始化 dp[0]=0;

遍历差序列,对于当前的数 d[i],如果在前面没出现过值为 d[i] 的数,那么这个数选或不选对于整体没有影响,

则 dp[i]=(dp[i-1]*2+1)%mod(两个 dp[i-1] 分别表示继承前 i-1 个的情况下第 i 个选或不选的答案,还有一个 1 表示前 i-1 个都不选,只选第 i 个的情况);

如果 d[i] 在前面的 j(j 为满足 d[k]=d[i](0<k<i)的所有数中最大的一个 k)的位置出现过,则 dp[i]=dp[i-1]*2+1-dp[j-1]-1=dp[i-1]*2-dp[j-1](减去的情况是继承前 j-1 个的情况下从 j 到 i-1 都不选并且选第 i 个的情况,还有一个 1 表示前 i-1 个都不选,只选第 i 个的情况)。

动态更新 d[i] 最后出现的位置即可,最后 dp[n-1] 即为结果。


本题结束,注意差为负数的情况以及各种边界问题和取模问题即可。

上代码:


#include <bits/stdc++.h>using namespace std;typedef long long LL;const LL maxn=2123456,mod=1e9+9;LL t,n,i,m,d[maxn],v[maxn*4],dp[maxn];int main(){scanf("%lld",&t);while(t--){scanf("%lld",&n);for(i=1;i<=n;i++)scanf("%lld",&d[i]);for(i=1,m=0;i<n;i++)d[i]=d[i+1]-d[i],m=min(m,d[i]);for(i=1;i<n;i++)d[i]-=m,v[d[i]]=-1;for(i=1;i<n;i++){if(~v[d[i]])dp[i]=(dp[i-1]*2-dp[v[d[i]]-1]+mod)%mod;elsedp[i]=(dp[i-1]*2+1)%mod;v[d[i]]=i;}printf("%lld\n",dp[n-1]);}return 0;}


原创粉丝点击
热门问题 老师的惩罚 人脸识别 我在镇武司摸鱼那些年 重生之率土为王 我在大康的咸鱼生活 盘龙之生命进化 天生仙种 凡人之先天五行 春回大明朝 姑娘不必设防,我是瞎子 脸上出来痘痘怎么办 眼袋不大有细纹怎么办? 慢性咽炎老咳嗽怎么办 咽炎干咳老不好怎么办 房顶非法鸽子笼子怎么办 鸽子翅膀骨折了怎么办 手被猫爪子破皮怎么办 去台湾用流量怎么办 上吊脖子太痛怎么办 沙发拐角有空调怎么办 报警警察不出警怎么办 驾校合同丢了怎么办 月经弄脏了床单怎么办 半夜到深圳机场怎么办 统计局来公司查怎么办 双离合严重堵车怎么办 健身俱乐部会员要退私教怎么办 感冒做剧烈运动怎么办 雪乐山滑雪怎么办卡 吉林省社保漏保怎么办 时时彩账户冻结怎么办 半夜到天津机场怎么办 小孩吃了避孕药怎么办 太阳能手表停了怎么办 太阳伞架坏了怎么办 通州自行车闪退怎么办? 台球厅生意不好怎么办 被水母咬了怎么办 被告不收判决书怎么办 律师完不成创收怎么办 保险业务员欺骗客户怎么办 德州扑克一样大怎么办 天气热没有空调怎么办 毕业证相片掉了怎么办 环世界肠道蠕虫怎么办 驾校时间过期了怎么办 过度劳累手疼怎么办 工商年检做错了怎么办 工商年检数字证书过期怎么办 工商年检过了怎么办 工商忘了年检怎么办