#sZSZybttg040105. 1539:简单题
1539:简单题
好的,我将这道题整理为清晰的题面格式,并补充样例解释、数据范围与时空限制:
题目描述
题目来源:CQOI 2006
有一个 个元素的数组,每个元素初始均为 。有 条指令,指令分为两种:
- 操作 :给定 ,将区间 的每个数反转( 变 , 变 );
- 操作 :给定 ,询问第 个元素的值(输出 或 )。
请按顺序处理所有指令,并对每个操作 输出一行答案。
输入格式
第一行包含两个整数 ,表示数组的长度和指令的条数。
接下来 行,每行描述一个操作:
- 若第一个数为 ,则接下来有两个整数 ,表示区间反转操作;
- 若第一个数为 ,则接下来有一个整数 ,表示询问操作。
输出格式
对于每个操作 ,输出一行一个整数( 或 ),表示该位置的值。
样例
样例输入
20 10
1 1 10
2 6
2 12
1 5 12
2 6
2 15
1 6 16
1 11 17
2 12
2 6
样例输出
1
0
0
0
1
1
样例说明
(原题中有详细的操作后数组变化表,这里用文字说明)
初始数组:(长度 20)
- 操作 1:反转 → 前 10 个变为 1,其余为 0;
- 操作 2:问第 6 个值 → 1;
- 操作 3:问第 12 个值 → 0;
- 操作 4:反转 → 位置 5~10 从 1 变 0,位置 11~12 从 0 变 1;
- 此时前 12 个:1,1,1,1,0,0,0,0,0,0,1,1
- 操作 5:问第 6 个值 → 0;
- 操作 6:问第 15 个值 → 0;
- 操作 7:反转 → 变化较多;
- 操作 8:反转 ;
- 操作 9:问第 12 个值 → 0;
- 操作 10:问第 6 个值 → 1。
数据范围
- 对于 的数据,;
- 对于 的数据,,保证 。
时空限制
- 时间:
- 内存:(512 MB)
提示
此题为 区间修改(异或 1)、单点查询 问题。
由于反转操作可以看作对区间内每个数加 1 再模 2(即异或 1),我们需要一个数据结构支持:
- 区间加 1(模 2 意义下);
- 单点查询(模 2 后的值)。
方法一:树状数组(差分思想)
将原数组 的差分数组 定义为 ( 表示异或),则:
- 区间 反转:;
- 单点查询 :。
这样就将区间修改转化为两个单点修改(异或 1),单点查询转化为前缀异或和查询。
可以用树状数组维护 数组的前缀异或和(因为异或运算满足结合律和交换律,树状数组可以维护)。
方法二:线段树
直接维护区间和,反转操作相当于区间值取反(),同时打懒标记。单点查询时递归到叶子节点返回。
由于 较大,树状数组常数更小,推荐使用方法一。
树状数组实现步骤:
- 初始化树状数组 全为 ;
- 对于操作 1():
add(L, 1)(即 );add(R+1, 1)(注意 );
- 对于操作 2():
- 输出
sum(i) % 2(即前缀异或和模 2,但树状数组维护的是异或和,直接sum(i) & 1即可)。
- 输出
复杂度:每次操作 。
注意:
- 异或操作在树状数组中仍可用加法实现,因为模 2 加法等价于异或;
- 树状数组的
add操作将对应位置的值加 1(模 2),sum操作返回前缀和模 2 的结果。