ABC234 G & H 题解

ABC234G Divide a Sequence

题面

题意:

给定一个长度为 \(n\) 的序列 \(A\),对于每一种把序列 \(A\) 分成 \(k\) 个子段(设为 \(B_1,B_2,\dots,B_n\))的方案(共有 \(2^{n-1}\) 种),定义其权值为 \(\prod\limits_{i=1}^k (\max(B_i)-\min(B_i))\),问所有划分权值的和 \(\mod998244353\) 的结果。

数据范围:\(1\le n\le3\times10^5\)\(1\le A_i\le10^9\)

可以列出一个很显然的 DP:设 \(f_i\) 表示划分完前 \(i\) 个数的所有方案权值的和。

转移:\(f_i=\sum\limits_{j=0}^{i-1}(f_j\times(\max(j+1,i)-\min(j+1,i)))\)

暴力是 \(\mathcal{O}(n^2)\) 的。

先把式子拆开, \(\max\)\(\min\) 分开考虑。

观察到对于每一个左端点,对应的 \(\max\) 系数不降、\(\min\) 系数不增,于是很自然地想到单调栈。

具体地,分别维护两个递增和递减的单调栈,栈顶记录两个元素 \(\{val, sumval\}\) 分别为栈顶对应的值和 \(\sum\limits_{j<i}\) \([j\) 对应的转移系数为 \(val]\times dp_j\)

可能有点抽象,建议画个图理解一下。

注意 \(A_i\) 的大小超过了模数,在做乘法时要先取模。

Code:https://atcoder.jp/contests/abc234/submissions/29942178

ABC234H Enumerate Pairs

题面

题意:

给定 \(n\) 个平面上的点 \((x_i,y_i)\) 和一个整数 \(K\),输出所有欧几里德距离 \(\le K\) 的点对。

保证点对数不超过 \(4\times10^5\)

数据范围:\(1\le n\le2\times10^5\)\(1\le K\le1.5\times10^9\)\(0\le x_i,y_i\le10^9\)

使用 k-D Tree 暴力做即可。

注意直接把子树内节点的所有坐标信息存下来并不会爆空间,因为按照方差建树的 k-D Tree 树高是 \(\mathcal{O}(\log n)\) 的。

当然最稳妥的方式还是直接剪枝,即 在到这个点控制的矩形的最小距离 \(>K\) 的时候直接返回 和 在到这个点的最大距离 \(\le K\) 的时候加入这个子树内的所有点。

Code1:https://atcoder.jp/contests/abc234/submissions/29939069

Code2:https://atcoder.jp/contests/abc234/submissions/29940278

posted @ 2022-03-08 15:08  csxsi  阅读(105)  评论(0编辑  收藏  举报