懒癌

  • 题目链接

    uoj#76

  • 题目大意

    \(n\) 个人,每个人都有一种状态 \(0\)\(1\) ,如果一个人在某天知道自己的状态为 \(1\) ,那么会在当天开枪自杀。

    每个人能知道其余若干人的状态,这构成一个有向图。

    人与人不会相互交流,所有人都知道这 \(n\) 个人中至少有一个人状态为 \(1\)

    一旦有人自杀则立即停止。

    求:对于所有 \(2^n-1\) 种可能状态,开枪时间和以及自杀人数和(同一天自杀算多个人),对 \(998244353\) 取模。

    \(n\le 3000\)

  • 题解

    首先考虑完全图。

    不难归纳证明出有 \(k\) 个人为 \(1\) 就是第 \(k\) 天,死 \(k\) 个人。

    我们考虑 \(dp\)

    然后考虑一个人的推理过程:肯定是先假设自己为 \(0\) ,然后对于所有的可能状态 \(S\)\(\max\{f_S\}+1\) 就是自己的开枪时间。

    那么我们可以枚举所有状态 \(S\) ,对于其中每一个状态为 \(1\)\(i\) ,有一个他能看到的状态 \(T\) ,再枚举他看不到的所有可能状态 \(X\) ,那么 \(t_i=\max\{f_{T\cup X}\}+1\) ,所以 \(f_S=\min\{t_i|i\in S\}\)

    考虑在 \(DAG\) 上转移,我们发现如果一个状态能结束当且仅当转移无环。对于一个人 \(i\in S\) ,转移相当于把自己变为 \(0\) ,将无出边的人变为 \(1\) 。那么我们考虑在补图上做这个事情。

    根据转移无环,那么我们将所以指向强联通分量的删去,就会得到一个 \(DAG\) (补图意义下)。

    接下来我们证明一个结论:

    一个状态 \(S\)\(f_S\) 为在这个 \(DAG\)\(S\) 中的点直接或间接能到达的点的个数。

    考虑按拓扑序从大到小归纳。

    对于一个空集,显然成立。

    那么考虑状态 \(S\) 的任意一个点 \(i\) ,我们将 \(i\) 变为 \(0\) 使得 \(i\) 所指的点变为 \(1\) ,那么由归纳假设知 \(t_i\) 为这个新状态 \(T\)\(f_T+1\) 。所以所有的 \(i\in S\)\(t_i\) 均满足这个结论,所以结论对于 \(S\) 成立。证毕。

    所以就是对于一个 \(DAG\) 求所有状态能到达的点的数量,随便怎么做都行。

posted @ 2021-03-16 22:13  leukocyte  阅读(126)  评论(0)    收藏  举报