题目:CF474D Flowers

传送门


DP?递推?

首先可以很快看出这是一道 DP 的题目,但与其说是 DP,还不如说是递推

大家还记得刚学递推时教练肯定讲过的一道经典例题吗?就是爬楼梯,一个有 \(n\) 阶的楼梯,一个人爬上去,每次可以爬一阶也可以爬两阶,问有多少种爬法?其实这道题也是一样的,只不过把 \(2\) 换成了 \(k\) 而已。

于是我们开始分析,定义 \(dp[i]\) 为吃 \(i\) 个蛋糕的吃法总数。

很容易看出,如果 \(i<k\),就不可以一口气吃掉,只能一个一个吃,方法为 \(1\) 种。

如果 \(i==k\),就既可以一个一个吃掉,也可以一口气全部吃完,方法为 \(2\) 种。

如果 \(i>k\),就有两种吃法,既可以先吃 \(i-1\) 个,然后再吃一个,也可以先吃 \(i-k\) 个,再吃 \(k\) 个。方法为 \(dp[i-1]+dp[i-k]\) 种。

最后记得要开 long long,而且要一边加一边模 \(1000000007\)。

核心代码:

if(dp[i])continue;
if(i<k)
dp[i]=1;
else if(i==k)
dp[i]=2;
else
dp[i]=(dp[i-1]+dp[i-k])%1000000007;
sum[i]=(sum[i-1]+dp[i])%1000000007;

因为一组数据只有一个 \(k\),但是有很多组关于这个 \(k\) 的测试点,所以可以用一个前缀和数组统计 \(dp_1\sim dp_i\) 的和,然后根据题目中 \(mod\ 1000000007\)。


玄学优化

其实这个优化也不难想到。既然一组数据中只会有一个 \(k\),那么说明不管怎么算,\(dp[i]\) 的值算出来都是相等的。那么可以判断一下当前出现的最大 \(x_2\),如果一组输入的 \(x_2\) 值小于最大值,就说明 \(dp[x_2]\) 已经计算过,直接输出即可。


\(Code\)

#include<bits/stdc++.h>
#define ll long long
using namespace std;
int t,k,x1,x2,Max=1;
ll dp[100005],sum[100005];
int main(){
scanf("%d %d",&t,&k);
while(t--){
scanf("%d %d",&x1,&x2);
if(Max>=x2){ //优化:判断x2和max(x2)的大小
printf("%lld\n",(sum[x2]-sum[x1-1])%1000000007);
continue;//直接跳过
}
for(int i=Max;i<=x2;i++){//只计算没计算过的
if(dp[i])continue;
if(i<k)
dp[i]=1;
else if(i==k)
dp[i]=2;
else
dp[i]=(dp[i-1]+dp[i-k])%1000000007;
sum[i]=(sum[i-1]+dp[i])%1000000007;
}
printf("%lld\n",(sum[x2]-sum[x1-1])%1000000007);
Max=x2;//更新Max的值
}
return 0;
}

究竟是什么地方错了?

然后你交上去发现WA了!

这也就是一个本蒟蒻在做题时犯的错误。

一般要取余的题都是一边计算一边取模,所以可能会造成dp数组中前面的值大于后面的值的情况。在最终计算 \(x_1\sim x_2\) 的时候做的减法运算可能是负数,负数取模就出事了。

那如何解决呢?其实很简单,只需要在取模之前再加上一个 \(1000000007\) 就可以了。

\(Code\)

#include<bits/stdc++.h>
#define ll long long
using namespace std;
int t,k,x1,x2,Max=1;
ll dp[100005],sum[100005];
int main(){
scanf("%d %d",&t,&k);
while(t--){
scanf("%d %d",&x1,&x2);
if(Max>=x2){
printf("%lld\n",(sum[x2]-sum[x1-1]+1000000007)%1000000007);
continue;
}
for(int i=Max;i<=x2;i++){
if(dp[i])continue;
if(i<k)
dp[i]=1;
else if(i==k)
dp[i]=2;
else
dp[i]=(dp[i-1]+dp[i-k])%1000000007;
sum[i]=(sum[i-1]+dp[i])%1000000007;
}
printf("%lld\n",(sum[x2]-sum[x1-1]+1000000007)%1000000007);
Max=x2;
}
return 0;
}

终于A了!www

CF474D Flowers 题解的更多相关文章

  1. CF474D. Flowers

    D. Flowers time limit per test 1.5 seconds memory limit per test 256 megabytes input standard input ...

  2. Luogu CF451E Devu and Flowers 题解报告

    题目传送门 [题目大意] 有n种颜色的花,第i种颜色的花有a[i]朵,从这些花中选m朵出来,问有多少种方案?答案对109+7取模 [思路分析] 这是一个多重集的组合数问题,答案就是:$$C_{n+m- ...

  3. CF740B Alyona and flowers 题解

    Content 有 \(n\) 个数 \(a_1,a_2,a_3,...,a_n\),给定 \(m\) 个区间,你可以选择一些区间使得它们的总和最大(也可以不选),求这个最大的总和. 数据范围:\(1 ...

  4. [题解] [CF451E] Devu and Flowers

    题面 题解 就是一个求\(\sum_{i= 1}^{n}x _ i = m\)的不重复多重集的个数, 我们可以由容斥原理得到: \[ ans = C_{n + m - 1}^{n - 1} - \su ...

  5. 题解 【POJ1157】LITTLE SHOP OF FLOWERS

    先把题目意思说一下: 你有F束花,编号为\(1\)~\(F\)(\(1<=F<=100\)),\(V\)个花瓶,编号为\(1\) ~\(V\)(\(1<=V<=100\)), ...

  6. CF451E Devu and Flowers (隔板法 容斥原理 Lucas定理 求逆元)

    Codeforces Round #258 (Div. 2) Devu and Flowers E. Devu and Flowers time limit per test 4 seconds me ...

  7. Codeforces Round #381 (Div. 2)B. Alyona and flowers(水题)

    B. Alyona and flowers Problem Description: Let's define a subarray as a segment of consecutive flowe ...

  8. CF459B Pashmak and Flowers (水

    Pashmak and Flowers Codeforces Round #261 (Div. 2) B. Pashmak and Flowers time limit per test 1 seco ...

  9. Codeforces Round #271 (Div. 2)题解【ABCDEF】

    Codeforces Round #271 (Div. 2) A - Keyboard 题意 给你一个字符串,问你这个字符串在键盘的位置往左边挪一位,或者往右边挪一位字符,这个字符串是什么样子 题解 ...

随机推荐

  1. hackthebox TheNotebook

    前言 只拿到了user,提权没成功--有wp说是CVE-2019-5736,我没打成. 打点 nmap-sV -v -A 10.10.10.230 端口扫描结果: PORT STATE SERVICE ...

  2. AcWing 1282. 搜索关键词

    给定n个长度不超过50的由小写英文字母组成的单词,以及一篇长为m的文章. 请问,有多少个单词在文章中出现了. #include<bits/stdc++.h> using namespace ...

  3. 21 shell Here Document/String

    Here Document 的用法 Here Document可以将它理解为"嵌入文档""内嵌文档""立即文档",它将命令需要处理的数据或者 ...

  4. Java实验项目二——打印某年某月日历

    Program:打印万年历(输入年份,月份,输出该月的日历,已知1900年1月1日是星期一), 要 求: (1)编写一个方法判断闰年: (2)编写一个方法判断某年某月有多少天: (3)编写一个方法计算 ...

  5. Python实现 利用朴素贝叶斯模型(NBC)进行问句意图分类

    目录 朴素贝叶斯分类(NBC) 程序简介 分类流程 字典(dict)构造:用于jieba分词和槽值替换 数据集构建 代码分析 另外:点击右下角魔法阵上的[显示目录],可以导航~~ 朴素贝叶斯分类(NB ...

  6. 重新梳理调度器——GMP 调度模型

    调度器--GMP 调度模型 Goroutine 调度器,它是负责在工作线程上分发准备运行的 goroutines. 首先在讲 GMP 调度模型之前,我们先了解为什么会有这个模型,之前的调度模型是什么样 ...

  7. 开发必备linux命令大全-稳赚不亏

    我们的服务一般都是在linux系统运行,因此了解一些关于linux命令是必须.接下来将一一详细介绍一些常用的linux的命令 文件操作 远程登录与操作 磁盘挂载 进程管理 启动和结束 系统性能参数查看 ...

  8. 入门Kubernetes-Service

    一.前言 前一篇文章通过 Deployment 实现了Pod中服务实现滚动更新/回滚等操作:在真实应用场景中,需要将一组Pod提供给外部访问.而且Pod生命周期是短暂的,在 Pod 的生命周期过程中, ...

  9. 让5G技术“智慧”生活

    1.通讯技术的发展历程     2.5G技术的指标和具体概述        3. 5G的三个关键技术及概述             4.5G的应用场景及业务及安全挑战 如果你认为5G带来的只是下载视频 ...

  10. 利用扫描仪形成PDF

    1.打开WPS,新建PDF,从扫描仪新建 2.合并PDF:按照顺序添加指定PDF,合并即可完成