其他分享
首页 > 其他分享> > acwing 4078. 01串

acwing 4078. 01串

作者:互联网

给定一个整数 k

现在,我们可以对 01

字符串进行如下操作:

选择其中恰好 k
个连续的 1,将它们都变为 0

如果一个 01
字符串可以通过若干次上述操作,变为一个全 0

字符串,那么就称这个字符串很优秀。

本题共需要回答 T
组询问,每组询问给定两个整数 l,r,并请你计算长度在 [l,r] 范围内的所有 01

字符串中优秀字符串的数量。
输入格式

第一行包含两个整数 T
和 k

接下来 T
行,每行包含两个整数 l,r


输出格式

共 T
行,第 i 行输出第 i 组询问的答案对 109+7

取模后的结果。
数据范围

前三个测试点满足 1≤T,k≤10

所有测试点满足 1≤T,k≤105,1≤l≤r≤105


输入样例:

3 2
1 3
2 3
4 4

输出样例:

6
5
5
presum[i]:表示长度为i的01串优秀字符串的数量

#include <iostream>
#include <cstring>
#include <algorithm>
using namespace std;
const int N = 1e5 + 10, mod = 1e9 + 7;
typedef long long LL;
LL presum[N];
int main(){
    int T, k;
    cin >> T >> k;
    presum[0] = 1;
    for(int i = 1; i < N; i ++){
    	if(i < k)presum[i] = presum[i - 1];//只有全都为0这一种可能
    	else presum[i] = (presum[i - k] + presum[i - 1]) % mod; //长度为i - k长度的字串长度 + i-1长度优秀字符串的数量
        //第二项不用说 第一项:样例有一个4 4的 一共有5种可能 0000 0011 0110 1100 1111 其中0000和1111就是通过persum[2]得出  
        //长度为2的时候一共有00 11两种可能 所以长度为4的时候不仅要计算0011 0110 1100这三项, 还要计算0000 1111这一部分, 这一部分的数量又完全和presum[2]的数量相等, 所以presum[i] = presum[i - k] + presum[i - 1]
    }
    presum[0] = 0;
    for(int i = 1; i < N; i ++){
    	presum[i] = (presum[i] + presum[i - 1]) % mod;
    }
    while(T --){
    	int l, r;
    	cin >> l >> r;
    	cout << ((presum[r] - presum[l - 1]) % mod + mod) % mod << endl;
    }
}

标签:01,4078,int,字符串,长度,presum,include,acwing
来源: https://www.cnblogs.com/jw-zhao/p/15582522.html