题解-CF617E XOR and Favorite Number
题面
给定 \(n,m,k\) 和 \(n\) 个数的序列 \(a_i\),\(m\) 次求区间 \([l,r]\) 中异或值为 \(k\) 的子序列个数。
数据范围:\(1\le n,m\le 10^5\),\(0\le k,a_i\le 10^6\)。
蒟蒻语
这题的莫队做法太一眼,谁都会是吧(
那么蒟蒻就来写一个过不了这题(会 MLE、TLE)但是可以在线且很有趣的做法:分块。
说不定谁去开大限制卡个离线蒟蒻解就成正解了。
蒟蒻解
设 \(f(l,r)\) 表示区间 \([l,r]\) 的异或值为 \(k\) 的子区间数。
设 \(cross(l,r)\) 表示区间左端点在 \([1,l]\) 右端点在 \([r,n]\) 的异或值为 \(k\) 的区间数。
先容斥一下(\(cross(l-1,r+1)\) 为了抵消掉 \(f(1,n)\) 中多余的部分):
\]
这东西前 \(3\) 项可以时空 \(\Theta(n)\) 求出,只是最后一项太恶心了,蒟蒻的方法是分块时空 \(\Theta(n\sqrt{n})\)(巨佬如果有更优做法一定要指教蒟蒻)。
设有 \(b_n\) 个块,每个块为 \([l_i,r_i]\)。
先预处理 \(i<j:cro_{i,j}=cross(r_i,l_j)\),做法同莫队,前缀和加 unordered_map。
再记 \(lc_{i,c}\) 表示 \([1,r_i]\) 中前缀和为 \(c\) 的个数,\(rc_{i,c}\) 表示 \([l_i,n]\) 中前缀和为 \(c\) 的个数。
求 \(cross(l,r)\) 时,设 \(lb=\max_{i=1}^{b_n} r_i\le l\),\(rb=\min_{i=1}^{b_n} l_i\ge r\)。
结果就是 \(cro_{lb,rb}\) 再加上
左端点在 \([r_{lb}+1,l]\) 右端点在 \([l_{rb},n]\) 的答案(用 \(rc\) 数组求)
和左端点在 \([1,r_{lb}]\) 右端点在 \([r,l_{rb}-1]\) 的答案(用 \(lc\) 数组求)
和左端点在 \([r_{lb}+1,l]\) 右端点在 \([r,l_{rb}-1]\) 的答案(用前缀和加 unordered_map)。
然后这题就做完了,别忘了这个做法过不了。
代码
#include <bits/stdc++.h>
using namespace std;
//Start
typedef long long ll;
typedef double db;
#define mp(a,b) make_pair(a,b)
#define x first
#define y second
#define be(a) a.begin()
#define en(a) a.end()
#define sz(a) int((a).size())
#define pb(a) push_back(a)
const int inf=0x3f3f3f3f;
const ll INF=0x3f3f3f3f3f3f3f3f;
//Data
const int N=1e5;
int n,m,k,sm[N+2];
int a[N+1]; ll la[N+2],ra[N+2];
unordered_map<int,int> cnt;
//Block
const int B=320;
int sz,b[N+1];
ll cro[B+2][B+2];
unordered_map<int,int> lc[B+2],rc[B+2];
void build(){
sz=sqrt(n);
for(int i=1;i<=n;i++) b[i]=(i-1)/sz+1;
for(int i=1;i<=b[n];i++)
for(int j=1;j<=min(sz*i,n);j++) lc[i][sm[j-1]]++;
for(int i=1;i<=b[n];i++)
for(int j=n;j>=sz*(i-1)+1;j--) rc[i][sm[j]]++;
for(int i=1;i<=b[n];i++){
for(int t=b[n];t>i;t--){
for(int j=sz*(t-1)+1;j<=min(sz*t,n);j++)
cro[i][t]+=lc[i][sm[j]^k];
cro[i][t]+=cro[i][t+1];
}
}
}
ll cross(int l,int r){
if(l<0||r>n) return 0;
int lb=b[l+1]-1,rb=b[r-1]+1;
ll res=cro[lb][rb];
cnt.clear();
for(int i=lb*sz+1;i<=l;i++) cnt[sm[i-1]]++;
for(int i=r;i<=min((rb-1)*sz,n);i++) res+=cnt[sm[i]^k];
for(int i=lb*sz+1;i<=l;i++) res+=rc[rb][sm[i-1]^k];
for(int i=r;i<=min((rb-1)*sz,n);i++) res+=lc[lb][sm[i]^k];
return res;
}
//Main
int main(){
ios::sync_with_stdio(0);
cin.tie(0),cout.tie(0);
cin>>n>>m>>k;
for(int i=1;i<=n;i++) cin>>a[i];
for(int i=1;i<=n;i++) sm[i]=sm[i-1]^a[i];
cnt.clear(),cnt[sm[0]]++;
for(int i=1;i<=n;i++) la[i]=la[i-1]+cnt[sm[i]^k],cnt[sm[i]]++;
cnt.clear(),cnt[sm[n]]++;
for(int i=n;i>=1;i--) ra[i]=ra[i+1]+cnt[sm[i-1]^k],cnt[sm[i-1]]++;
assert(la[n]==ra[1]);
// for(int i=1;i<=n;i++) cout<<la[i]<<' ';cout<<'\n';
// for(int i=1;i<=n;i++) cout<<ra[i]<<' ';cout<<'\n';
build();
for(int i=0;i<m;i++){
int l,r; cin>>l>>r;
cout<<ra[l]+la[r]-la[n]+cross(l-1,r+1)<<'\n';
}
return 0;
}
祝大家学习愉快!
题解-CF617E XOR and Favorite Number的更多相关文章
- CF617E XOR and Favorite Number
CF617E XOR and Favorite Number 已知一个序列 \(a_1,\ a_2,\ \cdots,\ a_n\) 和 \(k\) ,\(m\) 次询问给出 \(l,\ r\) ,求 ...
- [CF617E]XOR and Favorite Number/[CQOI2018]异或序列
题目大意: 给定一个长度为$n(n\leq10^5)$的数列$A$和数$k$$(A_i,k\leq10^6)$.$m$组询问,每次询问区间$[l,r]$中有多少对$i,j(l\leq i\leq j\ ...
- Codeforces Round #340 (Div. 2) E. XOR and Favorite Number 莫队算法
E. XOR and Favorite Number 题目连接: http://www.codeforces.com/contest/617/problem/E Descriptionww.co Bo ...
- Codeforces Round #340 (Div. 2) E. XOR and Favorite Number —— 莫队算法
题目链接:http://codeforces.com/problemset/problem/617/E E. XOR and Favorite Number time limit per test 4 ...
- Codeforces617 E . XOR and Favorite Number(莫队算法)
XOR and Favorite Number time limit per test: 4 seconds memory limit per test: 256 megabytes input: s ...
- Codeforeces 617E XOR and Favorite Number(莫队+小技巧)
E. XOR and Favorite Number time limit per test 4 seconds memory limit per test 256 megabytes input s ...
- XOR and Favorite Number(莫队算法+分块)
E. XOR and Favorite Number time limit per test 4 seconds memory limit per test 256 megabytes input s ...
- XOR and Favorite Number (莫对算法)
E. XOR and Favorite Number time limit per test 4 seconds memory limit per test 256 megabytes input s ...
- Codeforces Round #340 (Div. 2) E. XOR and Favorite Number 【莫队算法 + 异或和前缀和的巧妙】
任意门:http://codeforces.com/problemset/problem/617/E E. XOR and Favorite Number time limit per test 4 ...
随机推荐
- day92:flask:flask简介&基本运行&路由&HTTP请求和响应
目录 1.Flask简介 2.关于使用flask之前的准备 3.flask的基本运行 4.flask加载配置 5.传递路由参数(没有限定类型) 6.传递路由参数(通过路由转换器限定路由参数的类型) 7 ...
- mysql之冷备和mysqldump、mydumper、xtrabackup备份
1.冷备流程: 停库备份,冷备份一般用于非核心业务,这类业务一般都允许停库. 在停止数据库后,将数据文件拷贝出来,然后对原始数据文件进行备份. 流程: 1.关闭数据库备份 2.拷贝数 ...
- TensorFlow_笔记
Tensorflow 1.基本概念 TensorFlow是一个编程系统,使用图(graphs)来表示计算任务,图(graphs)中的节点称之为op(operation),一个op获得0个或多个Tens ...
- 学习笔记:[算法分析]数据结构与算法Python版
什么是算法分析 对比程序,还是算法? ❖如何对比两个程序? 看起来不同,但解决同一个问题的程序,哪个" 更好"? ❖程序和算法的区别 算法是对问题解决的分步描述 程序则是采用某种编 ...
- pdfFactory如何设置限制打印和浏览文档权限
当我们进行私密文件的分享时,除了要设置密码保护文件内容外,还要注意设置打印限制,防止他人利用打印的方式,进行纸质文件的传播. 在使用pdfFactory安全策略时,我们可以通过设定禁止打印的方式,完全 ...
- 在FL Studio中如何更好地为人声加上混响(进阶教程)
为人声加上混响是我们在处理人声过程中必不可少的一步.然而,除了直接在人声混音轨道加上混响插件进行调节以外,这里还有更为细节的做法可以达到更好的效果. 步骤一:使用均衡器 在为人声加上混响之前,我们应该 ...
- FL studio系列教程(十四):如何在FL Studio播放列表中排列样式
我们在FL Studio中做好了节奏样式后就可以在播放列表窗口中进行乐曲的编排了.刚接触这款软件的同学肯定会对如何编排比较陌生但也比较憧憬的,因为它是从一个窗口到另一个窗口中的操作.其实明白了这里的知 ...
- php 上传图片,无刷新上传,支持多图上传,远程图片上传
1 <html> 2 <head> 3 <meta http-equiv="Content-Type" content="text/html ...
- 工作中使用RabbitMQ
写一个基类 1 <?php 2 3 namespace BI\Service\RabbitMQJob; 4 5 use AMQPConnection; 6 use AMQPChannel; 7 ...
- PHP 获取本周、今日、本月的起始时间戳
当前周的开始时间(周一)$begintime = mktime(0, 0, 0, date('m'), (date('d') - (date('w')>0 ? date('w') : 7) + ...