Processing math: 5%

YZOJ P3942 gss2加强版

YZOJ P3942 gss2加强版

时间限制:2000MS      内存限制:524288KB

难度:7.0

  • 题目描述

给你 n 个数,你需要支持一下两种操作。

U x y:将第 x 个数修改成 y

Q x y:计算从第 x 个数至第 y 个数中不同数的和并输出。如对于一段数 1,2,3,2,7,它的值是 13=1+2+3+7

  • 输入格式

第一行 n 表示数的个数;

第二行包含这 n 个数;

第三行 m 表示操作次数;

接下来 m 行每行三个数表示题目描述的操作。

  • 输出格式

对于每个 Q 操作返回一个值。

  • 样例输入

  • 样例输出

  • 数据规模与约定

所有的输入均在 int  以内。

n \leq 100000 , m \leq 100000

 

 

Source: BZOJ 2883


 

 

 

思想类似于 P3706 ,求区间内不同数的和 等价于 区间内第一次出现的数的和。

所以可以维护每个位置上 上一个与它数值相同的位置 pre,对于区间 [l, r] ,若有 pre < l 则可以加入答案。

显然修改时会影响到其它位置的前驱,所以对于每种数用 std::set  维护相同数的位置。

询问相当于把每个位置看成二维坐标系中的一个点 \left(pre,i\right) ,并求 x \in [0, l-1], y \in [l, r] 的所有点的 a_i 之和。

显然可以用二维线段树维护。

还有一种线段树套平衡树的做法,空间复杂度会比较小。

时间复杂度都为 O(n \log^2 n)

 

 

 

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注