题目
思路
说明:
对向交换
在下文中称为弹性碰撞
,因为它确实和物理里的小球碰撞一模一样。
有关交点
令 f ( a ) f(a) f(a) 为第 a a a 架飞机将要飞到的地方。考虑这样一张图,由所有 a a a 向 f ( a ) f(a) f(a) 连边构成。不难发现,这是一个由很多环构成的图。
对于每一个环,我们断言:至少进行
∣
V
∣
−
1
|V|-1
∣V∣−1 次 弹性碰撞
,否则无法保持原序。
可以使用归纳法证明。对于 ∣ V ∣ = 1 |V|=1 ∣V∣=1 的情况显然成立。
对于 ∣ V ∣ > 1 |V|>1 ∣V∣>1 的情况,我们先随便取一个 a 0 a_0 a0,不妨设 f ( a 0 ) > a 0 f(a_0)>a_0 f(a0)>a0(小于的情况同理),取 a 1 = f ( a 0 ) , a 2 = f ( a 1 ) , … , a k = f ( a k − 1 ) ( k ≥ 2 ) a_1=f(a_0),\;a_2=f(a_1),\;\dots,\;a_k=f(a_{k-1})\;(k\ge 2) a1=f(a0),a2=f(a1),…,ak=f(ak−1)(k≥2) 满足 a 0 < a 1 < a 2 < ⋯ < a k − 1 a_0<a_1<a_2<\cdots<a_{k-1} a0<a1<a2<⋯<ak−1 但是 a k − 1 > a k a_{k-1}>a_k ak−1>ak(即第一个反序的位置)。这样的 k k k 必然存在,毕竟 a k ≤ n a_k\le n ak≤n 。
显然
a
k
−
1
→
a
k
a_{k-1}\rightarrow a_k
ak−1→ak 应当与
a
k
−
2
→
a
k
−
1
a_{k-2}\rightarrow a_{k-1}
ak−2→ak−1 相交(逆序对必然相交,拓扑学基本原理)。那么我们要求二者进行 弹性碰撞
,于是
f
(
a
k
−
1
)
=
a
k
−
1
f(a_{k-1})=a_{k-1}
f(ak−1)=ak−1 且
f
(
a
k
−
2
)
=
a
k
f(a_{k-2})=a_k
f(ak−2)=ak 。这样就使得一个飞机到达了正确位置,并且剩下的部分还是一个置换环(类似链表的删除)。归纳法可知需要
∣
V
∣
−
1
|V|-1
∣V∣−1 次。
上面证明了存在
∣
V
∣
−
1
|V|-1
∣V∣−1 的方案。同样容易证明的是,这是最优解。因为一次 弹性碰撞
最多使 置换环分裂成两个(画图易知),糟糕的情况下,可能把两个接成一个。最终的状态是
∣
V
∣
|V|
∣V∣ 个置换环,归纳法知
∣
V
∣
−
1
|V|-1
∣V∣−1 是下界。
交点本身怎么求?求逆序对即可。这可以用 s e t \tt set set 做。反正很简单啦。
特技操作
这道题……只有两种操作?(显然 C C C 只是为了糅进去另一个题而已,对方案规划无影响。)
总支出次数是定值?代价也是定值?这不跟这道大力分类讨论题一模一样嘛!常见套路:分类讨论。
- 如果弹性碰撞更便宜,那么我们使劲地进行
弹性碰撞
即可。显然这是合法的。正如题目中所说,弹性碰撞
不改变相对位置。 - 擦身而过更便宜,根据前面的说明,求至少要
弹性碰撞
多少次即可。
观察加分
斜的矩形不好做,考虑将其 旋转为边平行于坐标轴的正矩形。
我们只需要将其顺时针旋转 4 5 ∘ 45^{\circ} 45∘ 即可。其极角 θ \theta θ 可以用反三角函数来算。
然后扫描线。遇到矩形的左边,对 y y y 进行区间加;矩形的右边则减去。对一个点的查询就成为了单点查询覆盖次数。这可以用 离散化与树状数组 做。
代码
千言万语压在胸,最终只有一句浅吟低唱:对不起。