链接:https://www.nowcoder.com/acm/contest/140/A来源:牛客网

White Cloud is exercising in the playground.
White Cloud can walk 1 meters or run k meters per second.
Since White Cloud is tired,it can't run for two or more continuous seconds.
White Cloud will move L to R meters. It wants to know how many different ways there are to achieve its goal.
Two ways are different if and only if they move different meters or spend different seconds or in one second, one of them walks and the other runs.

输入描述:

The first line of input contains 2 integers Q and k.Q is the number of queries.(Q<=100000,2<=k<=100000)
For the next Q lines,each line contains two integers L and R.(1<=L<=R<=100000)

输出描述:

For each query,print a line which contains an integer,denoting the answer of the query modulo 1000000007.

输入例子:
3 3
3 3
1 4
1 5
输出例子:
2
7
11

-->

示例1

输入

复制

3 3
3 3
1 4
1 5

输出

复制

2
7
11

分析:题目让我们求从0到(l,r)的所有可能走法,每次可以走1或者k,但是走了k必须停一次

从0到x(1<=x<=n)每次走1或者k,不考虑停一次的种数符合递推式:

f(x) = f(x-1) + f(x-k)(x>=k) f(x) = 1(x>=1) f(0) = 0(x=0)

比赛时我是看其中k=2时符合斐波拉数列,于是想到了递推,然后推了3写出了递推式

然后我们看连续走k的情况,可以发现:

g(x) = 0(x<2*k) g(x) = x-k+1(2*k<=x<=3*k-1) g(x) = g(x-1) + g(x-k+1) (x>=3*k)

最后到x符合情况的种数就是:f(x)-g(x)

而每次要求到(l,r),我们可以先算个前缀和,在开始打表出所有值就行

当然k=1的时候,因为走和跑不同,所以不是每种都为1,计算一下可以发现符合斐波拉数列(可以考虑把走看成1,跑看成0,然后求在1中间插0的排列数)

#include <map>
#include <set>
#include <stack>
#include <cmath>
#include <queue>
#include <cstdio>
#include <vector>
#include <string>
#include <cstring>
#include <iomanip>
#include <iostream>
#include <algorithm>
#define debug(a) cout << #a << " " << a << endl
using namespace std;
const int maxn = 1e5;
const int mod = 1e9 + 7;
typedef long long ll;
ll a[10*maxn+10], sum[10*maxn+10], b[10*maxn+10];
int main() {
std::ios::sync_with_stdio(false);
ll n, k;
cin >> n >> k;
if( k != 1 ) {
sum[0] = 0;
for( ll i = 1; i <= k-1; i ++ ) {
a[i] = 1;
sum[i] = sum[i-1] + a[i];
}
a[k] = 2;
sum[k] = sum[k-1] + a[k];
ll num = 1;
for( ll i = 2*k; i <= 3*k-1; i ++ ) {
b[i] = num;
num ++;
}
for( ll i = k+1; i <= maxn; i ++ ) {
a[i] = ( a[i-1] + a[i-k] ) % mod;
if( i >= 3*k ) {
b[i] = ( b[i-1] + b[i-k+1] ) % mod;
sum[i] = ( sum[i-1] + ( a[i] - b[i] ) % mod ) % mod;
} else if( i < 3*k && i >= 2*k ) {
sum[i] = ( sum[i-1] + ( a[i] - b[i] ) % mod ) % mod;
} else {
sum[i] = ( sum[i-1] + a[i] ) % mod;
}
}
} else {
sum[1] = 2, sum[2] = 5;
a[1] = 2, a[2] = 3;
for( ll i = 3; i <= maxn; i ++ ) {
a[i] = ( a[i-1] + a[i-2] ) % mod;
sum[i] = ( sum[i-1] + a[i] ) % mod;
}
}
while( n -- ) {
ll le, ri;
cin >> le >> ri;
if( le == 1 ) {
cout << sum[ri] << endl;
} else {
cout << ( sum[ri] - sum[le-1] + mod ) % mod << endl;
}
}
return 0;
}

  

再贴一个dp的做法

f[i][0/1]表示已经跑了i米,最后一步是跑还是走的方案数。 f[i][1]=f[i-k][0],f[i][0]=f[i-1][0]+f[i-1][1] 答案即为l到r的f[i][0]和f[i][1]的累加 ,我们只需记录前缀和即可

#include <map>
#include <set>
#include <stack>
#include <cmath>
#include <queue>
#include <cstdio>
#include <vector>
#include <string>
#include <cstring>
#include <iomanip>
#include <iostream>
#include <algorithm>
#define debug(a) cout << #a << " " << a << endl
using namespace std;
const int maxn = 1e5;
const int mod = 1e9 + 7;
typedef long long ll;
ll sum[2*maxn], dp[2*maxn][3];
int main() {
std::ios::sync_with_stdio(false);
ll n, k, le, ri;
cin >> n >> k;
memset( dp, 0, sizeof(dp) );
memset( sum, 0, sizeof(sum) );
sum[0] = 0, dp[0][0] = 0, dp[0][1] = 0;
for( ll i = 1; i <= k; i ++ ) {
dp[i][0] = 1;
if( i == k ) {
dp[k][1] = 1;
}
sum[i] = ( dp[i][0] + dp[i][1] + sum[i-1] ) % mod;
}
for( ll i = k+1; i <= maxn; i ++ ) {
dp[i][0] = dp[i-1][0] + dp[i-1][1], dp[i][1] = dp[i-k][0];
sum[i] = ( sum[i-1] + dp[i][1] + dp[i][0] ) % mod;
}
while( n -- ) {
cin >> le >> ri;
cout << ( sum[ri] - sum[le-1] + mod ) % mod << endl;
}
return 0;
}

  

牛客网暑期ACM多校训练营(第二场) 题解 A run 递推 dp的更多相关文章

  1. 牛客网暑期ACM多校训练营 第九场

    HPrefix Sum study from : https://blog.csdn.net/mitsuha_/article/details/81774727 k较小.分离x和k. 另外的可能:求a ...

  2. 牛客网暑期ACM多校训练营(第四场):A Ternary String(欧拉降幂)

    链接:牛客网暑期ACM多校训练营(第四场):A Ternary String 题意:给出一段数列 s,只包含 0.1.2 三种数.每秒在每个 2 后面会插入一个 1 ,每个 1 后面会插入一个 0,之 ...

  3. 牛客网暑期ACM多校训练营(第五场):F - take

    链接:牛客网暑期ACM多校训练营(第五场):F - take 题意: Kanade有n个盒子,第i个盒子有p [i]概率有一个d [i]大小的钻石. 起初,Kanade有一颗0号钻石.她将从第1到第n ...

  4. 牛客网 暑期ACM多校训练营(第二场)A.run-动态规划 or 递推?

    牛客网暑期ACM多校训练营(第二场) 水博客. A.run 题意就是一个人一秒可以走1步或者跑K步,不能连续跑2秒,他从0开始移动,移动到[L,R]的某一点就可以结束.问一共有多少种移动的方式. 个人 ...

  5. 牛客网 暑期ACM多校训练营(第一场)A.Monotonic Matrix-矩阵转化为格子路径的非降路径计数,Lindström-Gessel-Viennot引理-组合数学

    牛客网暑期ACM多校训练营(第一场) A.Monotonic Matrix 这个题就是给你一个n*m的矩阵,往里面填{0,1,2}这三种数,要求是Ai,j⩽Ai+1,j,Ai,j⩽Ai,j+1 ,问你 ...

  6. 牛客网暑期ACM多校训练营(第三场)H Diff-prime Pairs (贡献)

    牛客网暑期ACM多校训练营(第三场)H Diff-prime Pairs (贡献) 链接:https://ac.nowcoder.com/acm/contest/141/H来源:牛客网 Eddy ha ...

  7. 2018牛客网暑期ACM多校训练营(第二场)I- car ( 思维)

    2018牛客网暑期ACM多校训练营(第二场)I- car 链接:https://ac.nowcoder.com/acm/contest/140/I来源:牛客网 时间限制:C/C++ 1秒,其他语言2秒 ...

  8. 牛客网暑期ACM多校训练营(第七场)Bit Compression

    链接:https://www.nowcoder.com/acm/contest/145/C 来源:牛客网 题目描述 A binary string s of length N = 2n is give ...

  9. 牛客网暑期ACM多校训练营(第一场) - J Different Integers(线段数组or莫队)

    链接:https://www.nowcoder.com/acm/contest/139/J来源:牛客网 时间限制:C/C++ 2秒,其他语言4秒 空间限制:C/C++ 524288K,其他语言1048 ...

  10. 牛客网暑期ACM多校训练营(第九场) A题 FWT

    链接:https://www.nowcoder.com/acm/contest/147/A来源:牛客网 Niuniu has recently learned how to use Gaussian ...

随机推荐

  1. 二叉查找树(查找、插入、删除)——C语言

    二叉查找树 二叉查找树(BST:Binary Search Tree)是一种特殊的二叉树,它改善了二叉树节点查找的效率.二叉查找树有以下性质: (1)若左子树不空,则左子树上所有节点的值均小于它的根节 ...

  2. cdh5-MariaDB 配置(暂未排版)

    在多数分布MariaDB的设施默认设置使用保守的缓冲区的大小和内存使用. 使用保守的缓冲区大小和内存使用率 Cloudera的数据库管理服务器,监控活动,报告管理,Cloudera 导航,Hive 的 ...

  3. 七天学会NodeJS——第一天

    转载请注明出处:葡萄城官网,葡萄城为开发者提供专业的开发工具.解决方案和服务,赋能开发者.原文出处:http://nqdeng.github.io/7-days-nodejs Node.js 是一个能 ...

  4. DedeCMS V5.7 SP2前台文件上传漏洞(CVE-2018-20129)

    DedeCMS V5.7 SP2前台文件上传漏洞(CVE-2018-20129) 一.漏洞描述 织梦内容管理系统(Dedecms)是一款PHP开源网站管理系统.Dedecms V5.7 SP2版本中的 ...

  5. java中File IO流的笔记

    1.File文件的属性和操作 boolean exists( )  判断文件或目录是否存在boolean isFile( )  判断是否是文件boolean isDirectory( ) 判断是否是目 ...

  6. JVM 内存模型概述

    我们都知道,Java程序在执行前首先会被编译成字节码文件,然后再由Java虚拟机执行这些字节码文件从而使得Java程序得以执行.事实上,在程序执行过程中,内存的使用和管理一直是值得关注的问题.Java ...

  7. Linux--shell编程原理--03

    一.编程原理: 1.编程介绍: 计算机只能识别二进制指令 程序=指令+数据 根据服务的重心不同,我们分为面向过程编程,面向对象编程: a) 面向过程:侧重于指令的编程语言 b) 面向对象:侧重于数据的 ...

  8. 最新 Flutter 团队工程师中文演讲 | Flutter 的性能测试和理论

    本视频为 Google Flutter 团队的软件工程师 Xiao Yu 在 2018 谷歌开发者大会做的演讲,演讲题目是<Flutter 的性能测试和理论>. 这个视频里将会通过近半个小 ...

  9. 汇总VSCode中比较好用的插件

    使用vscode编辑器两年的时间,总结出前端一些比较方便的插件 1. Auto Close Tag 自动添加HTML / XML关闭标签 2. Auto Complete Tag 自动完成标签 3 A ...

  10. Java中使用RestFul接口上传图片到阿里云OSS服务器

    1.接口方法 import java.io.IOException; import javax.servlet.http.HttpServletRequest; import org.springfr ...