Solution -「AGC 016F」Games on DAG
\(\mathcal{Description}\)
Link.
给定一个含 \(n\) 个点 \(m\) 条边的 DAG,有两枚初始在 1 号点和 2 号点的棋子。两人博弈,轮流移动其中一枚棋子到邻接结点位置,无法移动者负。求 \(2^m\) 个边集中,加入图中能使先手必胜的方案数。答案对 \(10^9+7\) 取模。
\(n\le15\)。
\(\mathcal{Solution}\)
先从博弈角度思考:两枚棋子显然独立,那么先手必胜等价于 \(\operatorname{sg}(1)\not=\operatorname{sg}(2)\),其中,\(\operatorname{sg}\) 有
\]
在不同边集的情况中,\(\operatorname{adj}(u)\) 有所改变,所以情况不同。
接下来,方便起见,尝试计数 \(\operatorname{sg}(1)=\operatorname{sg}(2)\) 的情况。令 \(f(S)~(1,2\in S)\) 表示仅考虑点集 \(S\) 的导出子图时,\(\operatorname{sg}(1)=\operatorname{sg}(2)\) 的方案数。而 DP 中的“子问题”源于 \(\operatorname{sg}\) 函数中 \(\operatorname{mex}\) 的定义——如果我们挑除所有 \(\operatorname{sg}(u)=0\) 的 \(u\)(一定存在)及其邻接边,剩下的子图仍然是同类问题,只是所有 \(\operatorname{sg}\) 值减少 \(1\),不影响 DP 定义,这就是转移的雏形。具体地,枚举点集 \(T\subseteq S\),钦定其中所有点的 \(\operatorname{sg}\) 非 \(0\),考虑:
\(1,2\in T\),\(T\) 中每个点至少连向一个 \(S-T\) 中的点,其余边任意(注意 \(T\) 中的边是子问题,不考虑)。
\(1,2\not\in T\),已经满足条件,在上种情况的基础上加上 \(T\) 中边任选的方案,直接贡献。
综上,复杂度 \(\mathcal O(3^nn)\)。
\(\mathcal{Code}\)
/* Clearink */
#include <cstdio>
#define rep( i, l, r ) for ( int i = l, repEnd##i = r; i <= repEnd##i; ++i )
#define per( i, r, l ) for ( int i = r, repEnd##i = l; i >= repEnd##i; --i )
const int MAXN = 15, MAXM = MAXN * ( MAXN - 1 ) >> 1, MOD = 1e9 + 7;
int n, m, pwr[MAXM + 5], conc[1 << MAXN][MAXN], f[1 << MAXN];
bool adj[MAXN + 5][MAXN + 5];
inline int mul( const long long a, const int b ) { return a * b % MOD; }
inline int sub( int a, const int b ) { return ( a -= b ) < 0 ? a + MOD : a; }
inline void subeq( int& a, const int b ) { ( a -= b ) < 0 && ( a += MOD ); }
inline int add( int a, const int b ) { return ( a += b ) < MOD ? a : a - MOD; }
inline void addeq( int& a, const int b ) { ( a += b ) >= MOD && ( a -= MOD ); }
int main() {
scanf( "%d %d", &n, &m ), pwr[0] = 1;
rep ( i, 1, m ) {
pwr[i] = add( pwr[i - 1], pwr[i - 1] );
int u, v; scanf( "%d %d", &u, &v );
adj[u - 1][v - 1] = true;
}
rep ( S, 1, ( 1 << n ) - 1 ) {
int v = 0; for ( ; !( S >> v & 1 ); ++v );
rep ( u, 0, n - 1 ) conc[S][u] = conc[S ^ 1 << v][u] + adj[u][v];
}
rep ( S, 0, ( 1 << n ) - 1 ) if ( ( S & 3 ) == 3 ) {
f[S] = 1;
for ( int T = S & ( S - 1 ); T; T = ( T - 1 ) & S ) {
if ( T & 1 && T & 2 ) {
int coe = 1;
rep ( u, 0, n - 1 ) if ( S >> u & 1 ) {
if ( T >> u & 1 ) {
coe = mul( coe, pwr[conc[S ^ T][u]] - 1 );
} else {
coe = mul( coe, pwr[conc[T][u]] );
}
}
addeq( f[S], mul( coe, f[T] ) );
} else if ( !( T & 1 || T & 2 ) ) {
int coe = 1;
rep ( u, 0, n - 1 ) if ( S >> u & 1 ) {
if ( T >> u & 1 ) {
coe = mul( coe,
mul( pwr[conc[S ^ T][u]] - 1, pwr[conc[T][u]] ) );
} else {
coe = mul( coe, pwr[conc[T][u]] );
}
}
addeq( f[S], coe );
}
}
}
printf( "%d\n", sub( pwr[m], f[( 1 << n ) - 1] ) );
return 0;
}
Solution -「AGC 016F」Games on DAG的更多相关文章
- Solution -「AGC 036D」「AT 5147」Negative Cycle
\(\mathcal{Descriprtion}\) Link. 在一个含 \(n\) 个结点的有向图中,存在边 \(\lang i,i+1,0\rang\),它们不能被删除:还有边 \(\l ...
- Solution -「AGC 026D」Histogram Coloring
\(\mathcal{Description}\) Link. 有 \(n\) 列下底对齐的方格纸排成一行,第 \(i\) 列有 \(h_i\) 个方格.将每个方格染成黑色或白色,求使得任意完 ...
- Solution -「AGC 004E」「AT 2045」Salvage Robots
\(\mathcal{Description}\) Link. 有一个 \(n\times m\) 的网格.每个格子要么是空的,要么有一个机器人,要么是一个出口(仅有一个).每次可以命令所有机 ...
- Solution -「AGC 012F」「AT 2366」Prefix Median
\(\mathcal{Description}\) Link. 给定序列 \(\{a_{2n-1}\}\),将 \(\{a_{2n-1}\}\) 按任意顺序排列后,令序列 \(b_i\) 为前 ...
- Solution -「AGC 010C」「AT 2304」Cleaning
\(\mathcal{Description}\) Link. 给定一棵 \(n\) 个点的无根树,点有点权,每次选择两个不同的叶子,使它们间的简单路径的所有点权 \(-1\),问能否将所有点 ...
- Solution -「AGC 019E」「AT 2704」Shuffle and Swap
\(\mathcal{Description}\) Link. 给定 \(01\) 序列 \(\{A_n\}\) 和 \(\{B_n\}\),其中 \(1\) 的个数均为 \(k\).记 \( ...
- Solution -「AGC 019F」「AT 2705」Yes or No
\(\mathcal{Description}\) Link. 有 \(n+m\) 个问题,其中 \(n\) 个答案为 yes,\(m\) 个答案为 no.每次你需要回答一个问题,然后得知这个 ...
- Solution -「AGC 013E」「AT 2371」Placing Squares
\(\mathcal{Description}\) Link. 给定一个长度为 \(n\) 的木板,木板上有 \(m\) 个标记点,第 \(i\) 个标记点距离木板左端点的距离为 \(x_i\ ...
- Solution -「AGC 003D」「AT 2004」Anticube
\(\mathcal{Description}\) Link. 给定 \(n\) 个数 \(a_i\),要求从中选出最多的数,满足任意两个数之积都不是完全立方数. \(n\le10^5\) ...
随机推荐
- CTF中的变量覆盖问题
0x00 前言 最近在干代码审计,于是就把之前学习的CTF题目中有关变量覆盖的题目结合下进一步研究. 通常将可以用自定义的参数值替换原有变量值的情况称为变量覆盖漏洞.经常导致变量覆盖漏洞场景有:$$使 ...
- 关于 Intel CPU 和Iris Xe Graphics的报告问题
关于 Intel CPU 和Iris Xe Graphics的报告问题 有些用户报告了一些技术问题,这里有更多的信息和如何解决. Intel 11th CPU & Iris Xe Graphi ...
- RHCSA 第四天
1.使用whereis 查找 locate命令 使用which查找whereis命令 使用locate查找rm命令 2.find命令使用: 使用find命令在当前路径下查找所有的普通文件 使用f ...
- 顺序表-Go语言实现
简单理解就是数组: 优缺点及使用场景 优点: 随机访问,在O(1)时间内找到第i个元素: 数据表中的数据是连续存放的,因此只要知道数据表中第一个元素的地址,那么后面的数据元素的地址就可以马上算出来. ...
- 与Elasticsearch交互的客户端
1.访问ES的方式 访问es的方式有两种,一种是http方式,还有一种是java客户端方式. 其中Java客户端又分为:1.1.Node client: 节点客户端实际上是一个集群中的节点(但不保存数 ...
- IoC容器-Bean管理注解方式(完全注解开发)
完全注解开发 (1)创建配置类,替代xml配置文件 (2)编写测试类 在实际中一般用springboot做
- 前端基础之javaScript(基本类型-布尔值数组-if-while)
目录 一:javaScript基本数据类型 1.字符串类型常用方法 2.返回长度 3.移出空白 4.移除左边的空白 5.移出右边的空格 6.返回第n个字符 7.子序列位置 8.根据索引获取子序列 9. ...
- docker 安装遇到404 not find
https://mirrors.ustc.edu.cn/docker-ce/linux/centos/docker-ce/repodata/repomd.xml: [Errno 14] HTTPS E ...
- 正向代理 、反向代理, 和 Linux系统配置nginx。
一.正向代理和反向代理的简单介绍. 2.代理 中间商,赚差价 在没有代理的时候: 茅台酒厂--->生产了一批酒--->通过物流发送到客户的家中/客户直接到酒厂购买酒--->突然有一个 ...
- 如何在 VS Code 中为 Java 类生成序列化版本号
前言 IDEA 提供自动生成序列化版本号的功能,其实 VS Code 也可以,只是默认关闭了这个功能,下面就来看看如何开启这个功能吧. 配置过程 首先需要保证 VS Code 上安装了提供 Java ...