部分在标签里面

AGC012B

水题但居然没想出来,主要是没看全各变量的数据范围。
法1是以距离为阶段,进行 dp 更新每个点对应扩张距离的最小时间戳。
法2时光倒流,每一步直接覆盖未覆盖点,dfs的轨迹可近似一棵叶子为未覆盖点的子树。
复杂度 O(nd)

ARC080E

最后操作即答案序列开头的两个数,一定一个下标在奇数另一个在偶数,贪心取值最小的位即可。
这样分成了三个子区间,然后不断迭代。具体用堆维护。

ARC080F

区间翻转,即区间异或1,差分后相当于异或两个位置。
由于哥德巴赫猜想:任意大于二的偶数可以拆成两个质数的和。
可以分讨为:差为奇质数(1),偶数(2),奇非质数(3)。
13贪心尽量多匹配。

ARC081E

建出子序列自动机,在上面按字典序bfs,找到第一处空节点即为答案。
当然从后往前dp也行。

ARC081F

一个矩形能翻转为全黑,取其中某点(x,y),将x行和y列上为0的翻转,此后不能再操作,可求最大全1矩形。
上面只是一种构造,总不能真的去翻转行列,转化为代数,(i,j)最终值为 !(x,y) xor !(x,j) xor !(i,y) xor (i,j),即矩形内每点满足 (x,y) xor (x,j) xor (i,y) xor (i,j)=1,这四个量好似矩形的四个角,则每个子矩形四角异或和为0可以拆成若干2×2小矩形异或和。因此判定就跟(x,y)无关了。接着可用悬线法求最大矩形(每点往左最远,往右最远,往上最远,保证每个极大矩形被更新到)

ARC083E

由于x是有关子树的信息,可以考虑儿子的 x 与之之间的关系,设y表示子树内异色点权和。

x(u)=c(u)=c(v)x(v)+c(u)!=c(v)y(v)+w(u)

注意w(u)是可以自由钦定的,所以对于一个子树x固定,需要让y尽量小。
这样就可以背包了,容积为x,值y最小,如果一个结点对应 x 更新不到那就impossible

ARC085F

设每个位置a值从01对答案的贡献为w(i),求前缀和为s(i)
设最后一次覆盖区间i的最小答案为f(i)。按右端点排序就可以求了,转移分不交和相交,线段树优化。

ARC086E

每层独立,且最后贡献为0/1。每层点建虚树,在其上面dp,f表示字数内点最后贡献为1的方案数。

ABC082D

蓝题但没想出来。
考虑每次转向,如果T个数为奇数垂直方向,否则水平方向走。
因此操作变为了若干步数和方向(x or y?),因此x和y轴相独立,dp会MLE,用bitset来优化。

ARC156D

两个字符串的限制很难处理,先退化为开头字符的大小关系。
按小到大连边,如果存在环,则一定有相等的位置,缩点。限制就往后移位继续连边。

ARC156E

第一步和ARC150D一样,在所在连通块 sz>k 的点中选,扩张到在未删的所有点中选(选出来后再判断合法)和原问题结果等价。因为满足连通块 sz>k 的有意义的每个点被选的概率等价,而其余无意义点选中也无影响。
ARC150D之后就利用期望线性性,答案为每个点被选中的期望次数求和。
这里求的是删点次数,而每个过程中存在的 sz>k 的连通块都会被删一次 (贡献答案1次),所以可以求 sz>k 连通块出现概率和。
连通块出现要保证外圈必须要删的点(m个),全都要在联通块内的点(n个)之前出现,当然其它的点就一点也不影响了,所以概率是n!m!(n+m)!,由于是连通块信息求和,树上背包,O(n3)解决。

ARC165F

结论:若 li<ljri<rji 一定在 j 之前。否则包含关系,谁前谁后答案一样。
不会证明ing~
所以偏序建图,按字典序拓扑排序,复杂度 O(n2)
考虑线段树优化建图:按 l 从大到小扫描线,维护以 r 为下标的线段树,相当于连向 r 一段后缀区间,而新添加的 r 不能影响之前的连边,所以要可持久化一下。

ARC058E

X+Y+Z17,可以想到状压。从前往后加每个数且维护状态:初始为0,每加入一个数d,就在后面加上d位的1000...,只需要截取前17位,这样也可以判断题目中的段是否出现过。

点击查看代码
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
const int mod = 1e9 + 7;
ll f[45][1 << 17];
void Add(ll &x, ll y) {x = (x + y) % mod;}
ll ksm(ll a, ll b) {ll res(1); for(; b; b >>= 1, a = a * a % mod) if(b & 1) res = res * a % mod; return res;}
int main() {
    int n, X, Y, Z, all, end;
    scanf("%d%d%d%d", &n, &X, &Y, &Z);
    end = (1 << (Z - 1)) | (1 << (Z + Y - 1)) | (1 << (X + Y + Z - 1));
    all = (1 << (X + Y + Z)) - 1; 
    // printf("!end=%d all=%d\n", end, all);
    f[0][0] = 1;
    for(int i = 1; i <= n; i++) {
        for(int s = 0; s <= all; s++) {
            // printf("f(%d,%d)=%lld\n", i - 1, s, f[i - 1][s]);
            if(!f[i - 1][s]) continue;
            for(int j = 1; j <= 10; j++) {
                int s_ = (s << 1 | 1) << (j - 1);
                s_ &= all;
                if((s_ & end) != end) {Add(f[i][s_], f[i - 1][s]);}
                // printf("!f(%d,%d)=%lld %lld\n", i, s_, f[i][s_], f[i - 1][s]);
            }
        }
    }
    ll ans = 0;
    for(int s = 0; s <= all; s++) {Add(ans, f[n][s]);}
    printf("%lld", (ksm(10, n) - ans + mod) % mod);
    return 0;
}

ARC093E

先求出 MST。所有染色的最小生成树:一定是原 MST 或者原 MST 加入一条新边,删去一条原边所得。
先令 MST 同色,然后把其它非树边分为使值 =X<X>X
<X的部分一定与原 MST 相同,=X的部分至少要存在一个与 原MST 不同,其余随便填色。
特别的 MST=X,原 MST 可存在两种颜色。

ARC094F

关键的转化:把 a, b, c 看成 0, 1, 2 ,发现总和模 3 意义下不变,而且模 3 为定值的条件还是充分的,DP即可。