CF1670F Jee, You See?

cxqghzj·2024-09-10 21:49·10 次阅读

CF1670F Jee, You See?

题意#

给定 n,l,r,z,计算长度为 n 的序列的数量,使得:

  • lair
  • a1a2...an=z

109 取模。

n103,lr1018,z1018

Sol#

对于 [l,r] 的问题,经典数位 dp 差分一下。

考虑数位 dp,从低位向高位确定,设 fx,num,0/1 表示确定 [x,len] 之间的二进制位,上一位向第 x 位进了 num 位,是否小于等于和的限制。

考虑枚举当前位选择的个数,乘上组合数,做完了。

复杂度:O(n2×log)

Code#

Copy
#include <iostream> #include <algorithm> #include <cstdio> #include <array> #define ll long long using namespace std; #ifdef ONLINE_JUDGE #define getchar() (p1 == p2 && (p2 = (p1 = buf) + fread(buf, 1, 1 << 21, stdin), p1 == p2) ? EOF : *p1++) char buf[1 << 23], *p1 = buf, *p2 = buf, ubuf[1 << 23], *u = ubuf; #endif ll read() { ll p = 0, flg = 1; char c = getchar(); while (c < '0' || c > '9') { if (c == '-') flg = -1; c = getchar(); } while (c >= '0' && c <= '9') { p = p * 10 + c - '0'; c = getchar(); } return p * flg; } void write(int x) { if (x < 0) { x = -x; putchar('-'); } if (x > 9) { write(x / 10); } putchar(x % 10 + '0'); } bool _stmer; const int N = 1e3 + 5, M = 65, mod = 1e9 + 7; void Mod(int &x) { if (x >= mod) x -= mod; if (x < 0) x += mod; } array <array <int, N>, N> C; void init(int n) { C[0][0] = 1; for (int i = 1; i <= n; i++) { C[i][0] = 1; for (int j = 1; j <= i; j++) C[i][j] = C[i - 1][j] + C[i - 1][j - 1], Mod(C[i][j]); } } array <array <array <int, 2>, N>, M> f; array <int, M> s; int dfs(int x, int num, int flg, int len, int n, ll res) { if (~f[x][num][flg]) return f[x][num][flg]; if (x > len) return f[x][num][flg] = (!num && !flg); f[x][num][flg] = 0; for (int i = 0; i <= n; i++) { if (((res >> (x - 1)) & 1) != (i & 1)) continue; int now = ((i + num) & 1), _flg = (now < s[x]) ? 0 : (now == s[x] ? flg : 1); f[x][num][flg] += 1ll * dfs(x + 1, (i + num) >> 1, _flg, len, n, res) * C[n][i] % mod; Mod(f[x][num][flg]); } /* cerr << x << " " << num << " " << flg << " " << f[x][num][flg] << endl; */ return f[x][num][flg]; } int solve(int n, ll x, ll k) { if (!x || x < k) return 0; for (int i = 0; i < M; i++) for (int j = 0; j < N; j++) f[i][j].fill(-1); int cnt = 0; ll tp = x; while (tp) { cnt++; s[cnt] = tp & 1; tp >>= 1; } return dfs(1, 0, 0, cnt, n, k); } bool _edmer; int main() { cerr << (&_stmer - &_edmer) / 1024.0 / 1024.0 << "MB\n"; init(1000); int n = read(); ll l = read(), r = read(), k = read(); /* cerr << solve(n, 0, k) << "@" << endl; */ write((solve(n, r, k) - solve(n, l - 1, k) + mod) % mod), puts(""); return 0; }
posted @   cxqghzj  阅读(10)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· 25岁的心里话
· 闲置电脑爆改个人服务器(超详细) #公网映射 #Vmware虚拟网络编辑器
· 零经验选手,Compose 一天开发一款小游戏!
· 因为Apifox不支持离线,我果断选择了Apipost!
· 通过 API 将Deepseek响应流式内容输出到前端
点击右上角即可分享
微信分享提示
目录