洛谷P17591题解

分析

题意

给定一个二进制表示的大数 xx 和整数 kk,求有多少个数字 yy,满足至少 kk 次规定操作能把 yy 变成 xx。

规定操作:每次对 yy 执行 y + lowbit(y) 或 y - lowbit(y)(lowbit(y) 是 yy 二进制最低位的数值)。答案对 109+710^9+7 取模。

思路

  1. 先找到 xx 二进制末尾连续 00 的长度 LL。
  2. 若要求的操作次数 k>Lk > L,没有符合条件的 yy,答案为 00;
  3. 若 k≤Lk \le L,答案:2L+1−2k2^{L+1} - 2^k(对 109+710^9+7 取模)。

代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
const int MOD = 1e9 + 7;
const int P = 5e6 + 5;
ll pow2[P];
void pre() {
pow2[0] = 1;
for (int i = 1; i < P; i++) {
pow2[i] = (pow2[i - 1] * 2LL) % MOD;
}
}
const int N = 1e6 + 5;
char s[N];
int main() {
pre();
int T;
cin >> T;
while (T--) {
int n, k;
cin >> n >> k >> s;
int L = 0;
char c = s[n - 1];
for (int i = n - 1; i >= 0; i--) {
if (s[i] == c) L++;
else break;
}
ll ans;
if (k > L) ans = 0;
else ans = (pow2[L + 1] - pow2[k] + MOD) % MOD;
cout << ans << endl;
}
return 0;
}

洛谷P17591题解
https://lijingshu2014.github.io/2026/10/04/洛谷P17591题解/
作者
lijingshu
发布于
2026年10月4日
许可协议