题意

从$1 - n$中任意选择一些数,选$m$次构成$m$个集合

保证:

  • 集合不为空
  • 任意两个集合不相同
  • 集合内各个元素xor起来等于0

Sol

神仙题Orz

我看到两种做法,一种是洛谷题解上的直接dp,另一种是yyb的神仙转化。

其实都差不多吧。。

我简单说一下,设$f[i]$表示选了$i$个集合,满足条件的方案

直接转移会非常麻烦,因为要同时限制集合不同 xor不为0,我们又不知道集合的具体元素。

因此我们考虑容斥。

为了方便考虑,我们先不考虑每个元素的位置,最后再除以$M!$

因为xor的性质,若我们已经知道了前$i - 1$个元素,那么我们这时候选什么是确定的。

先确定出前$i - 1$个数,方案数为$A_{2^n - 1}^{i - 1}$,

考虑若此时选了一个空的集合,那我们要保证前$i - 1$个集合满足条件,方案数为$f[i - 1]$

若选了重复的集合(这是最难理清楚的),剩下的$i - 2$个元素很定要满足条件,方案数为$f[i - 2]$,然后我们枚举一个集合,方案数为$2^{n} - (i - 2)$,这样看似就可以了。但是我们在递推的时候是没有考虑顺序的,因此另一个元素有$i - 1$种取值,因此还要乘$i - 1$

得到递推式

f[i]=A_{2^n-1}^{i-1}-f[i-1]-(i-1)\times f[i-2]\times(2^n-1-(i-2))

// luogu-judger-enable-o2
#include<iostream>
#include<algorithm>
#include<cstdio>
#include<stack>
#include<vector>
#include<cstring>
#define LL long long
//#define int long long
using namespace std;
const int MAXN = 3 * 1e6;
const LL mod = 1e8 + 7;//fuck
inline int read() {char c = getchar(); int x = 0, f = 1;while(c < '0' || c > '9'){if(c == '-') f = -1; c = getchar();}while(c >= '0' && c <= '9') x = x * 10 + c - '0', c = getchar();return x * f;
}
int N, M;
LL ifac[MAXN], fac[MAXN], f[MAXN], A[MAXN];
LL fastpow(LL a, LL p) {LL base = 1;while(p) {if(p & 1) base = (base * a) % mod;a = (a * a) % mod; p >>= 1;}return base % mod;
}
main() {N = read(); M = read(); LL base = fastpow(2, N) % mod;fac[0] = A[0] = 1; for(int i = 1; i <= M; i++) fac[i] = 1ll * i * fac[i - 1] % mod;ifac[M] = fastpow(fac[M], mod - 2);for(int i = 1; i <= M; i++) A[i] = 1ll * A[i - 1] * (base - i + mod) % mod;f[0] = 1; f[1] = 0; for(int i = 2; i <= M; i++) f[i] = ((A[i - 1] - f[i - 1] + mod) % mod - 1ll * f[i - 2] * (i - 1) % mod * (base - i + 1) % mod + mod) % mod;printf("%lld", f[M] * ifac[M] % mod);return 0;
}
/*
99999 99999
*/

转载于:https://www.cnblogs.com/zwfymqz/p/9540625.html

BZOJ2339: [HNOI2011]卡农(dp 容斥)相关推荐

  1. bzoj2339[HNOI2011]卡农 dp+容斥

    2339: [HNOI2011]卡农 Time Limit: 10 Sec  Memory Limit: 128 MB Submit: 842  Solved: 510 [Submit][Status ...

  2. [BZOJ2339][HNOI2011]卡农

    [BZOJ2339][HNOI2011]卡农 试题描述 输入 见"试题描述" 输出 见"试题描述" 输入示例 见"试题描述" 输出示例 见& ...

  3. P3214 [HNOI2011] 卡农 题解

    P3214 [HNOI2011] 卡农 文章目录 代码 题解 前言 正文 要素 代码 #include <bits/stdc++.h> using namespace std;#defin ...

  4. P5405-[CTS2019]氪金手游【树形dp,容斥,数学期望】

    前言 话说在LojLojLoj下了个数据发现这题的名字叫fgofgofgo 正题 题目链接:https://www.luogu.com.cn/problem/P5405 题目大意 nnn张卡的权值为1 ...

  5. [HNOI2011] 卡农 题解

    众所周知卡农是一种复调音乐的写作技法,小余在听卡农音乐时灵感大发,发明了一种新的音乐谱写规则. 他将声音分成 nn 个音阶,并将音乐分成若干个片段.音乐的每个片段都是由 11 到 nn 个音阶构成的和 ...

  6. CF296B dp\容斥

    传送门 文章目录 题意: 思路: 题意: n≤1e5n\le1e5n≤1e5 思路: 求方案数基本就是考虑dpdpdp了,看到nnn这么大可以考虑一下分情况讨论的dpdpdp状态. 设f[i][j]f ...

  7. [CQOI2012] 局部极小值(状压DP + 容斥 + 搜索)

    problem luogu-P3160 solution 这么小的数据范围,非暴力不状压.暴力 O(28!)O(28!)O(28!) 呵呵呵可以拉走了. 我们不妨从小到大填数字,这样如果局部极小值点还 ...

  8. AT4352-[ARC101C] Ribbons on Tree【dp,容斥】

    正题 题目链接: https://www.luogu.com.cn/problem/AT4352 https://atcoder.jp/contests/arc101/tasks/arc101_c 题 ...

  9. bzoj 1042: [HAOI2008]硬币购物(dp+容斥)

    1042: [HAOI2008]硬币购物 Time Limit: 10 Sec  Memory Limit: 162 MB Submit: 2555  Solved: 1537 [Submit][St ...

最新文章

  1. python 列表算平均分_python平均列表
  2. jstl 获取 javascript 定义的变量_一个后端开发者前端语言基础:JavaScript
  3. mysql练习数据_数据分析学习第一关-入门
  4. linux 查看其他磁盘分区,Linux 查看磁盘分区.pdf
  5. “公益AI之星”挑战赛-新冠疫情相似句对判定大赛
  6. GPS测量中所涉及的时间系统
  7. 【预测模型-ELAMN预测】基于哈里斯鹰算法优化ELMAN神经网络实现数据回归预测matlab代码
  8. Android N for Developers
  9. PTA 7-47 打印选课学生名单分数 25 分 (C 邻接表+二叉排序树 )
  10. SpringBoot在controller返回一个HTML页面
  11. 《基于小型训练集的深度学习迁移的食用毒蘑菇机器视觉识别系统》论文笔记
  12. 求两点之间最短路径-Dijkstra算法
  13. 会员权益营销中,等级会员的五种权益设置
  14. 1对多业务,数据库水平切分架构一次搞定 | 架构师之路
  15. HTML视频:视频播放网页
  16. 2020-12-20随笔
  17. oracle 根据出生年份计算生肖
  18. 传统商城系统的痛点分析
  19. BUGKU------中国菜刀
  20. vue项目实录:下拉刷新组件的开发及slot的使用

热门文章

  1. LightOJ - 1098 A New Function
  2. python基础---面向过程编程
  3. 文件操作:在某手诗文中插入一句话
  4. XenApp_XenDesktop_7.6实战篇之十五:StoreFront的配置
  5. 运维-系统架构师经验总结:
  6. autofac文档:服务类型,名称和键
  7. 在VC++中创建DLL文件并加载
  8. 通过ObjectMapper将实体转成字符串 ,将 用json存的的list 回转list
  9. DOS命令下Javac命令不能执行原因
  10. java根据经纬度坐标计算两点的距离算法