https://www.lydsy.com/JudgeOnline/problem.php?id=4137

https://www.luogu.org/problemnew/show/P4585

火星上的一条商业街里按照商店的编号1,2 ,…,n ,依次排列着n个商店。商店里出售的琳琅满目的商品中,每种商品都用一个非负整数val来标价。每个商店每天都有可能进一些新商品,其标价可能与已有商品相同。 
火星人在这条商业街购物时,通常会逛这条商业街某一段路上的所有商店,譬如说商店编号在区间[L,R]中的商店,从中挑选1件自己最喜欢的商品。每个火星人对商品的喜好标准各不相同。通常每个火星人都有一个自己的喜好密码x。对每种标价为val的商品,喜好密码为x的火星人对这种商品的喜好程度与val异或x的值成正比。也就是说,val xor x的值越大,他就越喜欢该商品。每个火星人的购物卡在所有商店中只能购买最近d天内(含当天)进货的商品。另外,每个商店都有一种特殊商品不受进货日期限制,每位火星人在任何时刻都可以选择该特殊商品。每个商店中每种商品都能保证供应,不存在商品缺货的问题。 
对于给定的按时间顺序排列的事件,计算每个购物的火星人的在本次购物活动中最喜欢的商品,即输出val xor x的最大值。这里所说的按时间顺序排列的事件是指以下2种事件: 
事件0,用三个整数0,s,v,表示编号为s的商店在当日新进一种标价为v 的商品。 
事件1,用5个整数1,L,R,x,d,表示一位火星人当日在编号为L到R的商店购买d天内的商品,该火星人的喜好密码为x。

参考:https://blog.csdn.net/lvzelong2014/article/details/78688727

继续练习线段树分治,虽然还是离不开题解但是已经知道拿什么分治了。

以及越来越深感线段树分治并不是线段树这一个事实了,开个专栏吧。

显然d的存在使得一些商品被“撤销”了,但是每个人的d都是不同的,我们就没法把商品放到线段树上。

于是反其道而行之,把人扔到线段树上,把商品放到线段树上跑。

然后每次询问异或最大值就是可持久化trie了。

PS:时刻注意这里面有两个量:商品所在的商店,以及商品上货时间。不要搞混了。

我们预先按照商店排序,然后根据当前的时间区间再重新分配即可(有点像整体二分)。

#include<cmath>
#include<queue>
#include<vector>
#include<cstdio>
#include<cctype>
#include<cstring>
#include<iostream>
#include<algorithm>
using namespace std;
typedef long long ll;
const int N=1e5+;
const int B=;
inline int read(){
int X=,w=;char ch=;
while(!isdigit(ch)){w|=ch=='-';ch=getchar();}
while(isdigit(ch))X=(X<<)+(X<<)+(ch^),ch=getchar();
return w?-X:X;
}
struct data{
int l,r,x,L,R;
}p[N];
struct good{
int s,v,t;
}q[N],tmpl[N],tmpr[N];
struct node{
int son[],sum;
}tr[N*];
int n,m,pcnt,qcnt,ans[N],rt[N],num[N],pool;
vector<int>seg[N*];
inline bool cmp(good a,good b){
return a.s<b.s;
}
void insert(int y,int &x,int k,int now){
tr[x=++pool]=tr[y];
tr[x].sum++;
if(now<)return;
bool p=k&(<<now);
insert(tr[y].son[p],tr[x].son[p],k,now-);
return;
}
int query(int nl,int nr,int k,int now){
if(now<)return ;
bool p=k&(<<now);
int delta=tr[tr[nr].son[p^]].sum-tr[tr[nl].son[p^]].sum;
if(delta>)return (<<now)+query(tr[nl].son[p^],tr[nr].son[p^],k,now-);
else return query(tr[nl].son[p],tr[nr].son[p],k,now-);
}
void add(int a,int l,int r,int l1,int r1,int x){
if(r<l1||r1<l)return;
if(l1<=l&&r<=r1){
seg[a].push_back(x);return;
}
int mid=(l+r)>>;
add(a<<,l,mid,l1,r1,x);add(a<<|,mid+,r,l1,r1,x);
}
int find(int l,int r,int k){
l--;
while(l<r){
int mid=(l+r+)>>;
if(num[mid]<=k)l=mid;
else r=mid-;
}
return l;
}
void work(int a,int l,int r){
pool=;int cnt=;
for(int i=l;i<=r;i++){
num[++cnt]=q[i].s;
insert(rt[cnt-],rt[cnt],q[i].v,B);
}
for(int i=;i<seg[a].size();i++){
int id=seg[a][i];
int L=find(,cnt,p[id].l-),R=find(,cnt,p[id].r);
ans[id]=max(ans[id],query(rt[L],rt[R],p[id].x,B));
}
}
void divide(int a,int l,int r,int l1,int r1){
int mid=(l+r)>>,len1=,len2=;
work(a,l1,r1);
for(int i=l1;i<=r1;i++){
if(q[i].t<=mid)tmpl[len1++]=q[i];
else tmpr[len2++]=q[i];
}
for(int i=;i<len1;i++)q[i+l1]=tmpl[i];
for(int i=;i<len2;i++)q[i+l1+len1]=tmpr[i];
if(l==r)return;
divide(a<<,l,mid,l1,l1+len1-);
divide(a<<|,mid+,r,l1+len1,r1);
}
int main(){
n=read(),m=read();
for(int i=;i<=n;i++)insert(rt[i-],rt[i],read(),B);
for(int i=;i<=m;i++){
int op=read();
if(!op){
q[++qcnt].s=read();q[qcnt].v=read();
q[qcnt].t=qcnt;
}else{
p[++pcnt].l=read();p[pcnt].r=read();
p[pcnt].x=read();int d=read();
p[pcnt].L=max(qcnt-d+,);p[pcnt].R=qcnt;
ans[pcnt]=query(rt[p[pcnt].l-],rt[p[pcnt].r],p[pcnt].x,B);
}
}
for(int i=;i<=pcnt;i++)add(,,qcnt,p[i].L,p[i].R,i);
sort(q+,q+qcnt+,cmp);
divide(,,qcnt,,qcnt);
for(int i=;i<=pcnt;i++)printf("%d\n",ans[i]);
return ;
}

+++++++++++++++++++++++++++++++++++++++++++

+本文作者:luyouqi233。               +

+欢迎访问我的博客:http://www.cnblogs.com/luyouqi233/+

+++++++++++++++++++++++++++++++++++++++++++

BZOJ4137 & 洛谷4585:[FJOI2015]火星商店问题的更多相关文章

  1. 洛谷 P4585 [FJOI2015]火星商店问题 解题报告

    P4585 [FJOI2015]火星商店问题 题目描述 火星上的一条商业街里按照商店的编号\(1,2,\dots,n\) ,依次排列着\(n\)个商店.商店里出售的琳琅满目的商品中,每种商品都用一个非 ...

  2. [洛谷P4585] [FJOI2015] 火星商店问题

    Description 火星上的一条商业街里按照商店的编号 \(1\),\(2\) ,-,\(n\) ,依次排列着 \(n\) 个商店.商店里出售的琳琅满目的商品中,每种商品都用一个非负整数 \(va ...

  3. 洛谷$P4585\ [FJOI2015]$火星商店问题 线段树+$trie$树

    正解:线段树+$trie$树 解题报告: 传送门$QwQ$ $umm$题目有点儿长我先写下题目大意趴$QwQ$,就说有$n$个初始均为空的集合和$m$次操作,每次操作为向某个集合内加入一个数$x$,或 ...

  4. 洛谷 P4585 [FJOI2015]火星商店问题

    (勿看,仅作笔记) bzoj权限题... https://www.luogu.org/problemnew/show/P4585 对于特殊商品,直接可持久化trie处理一下即可 剩下的,想了一段时间c ...

  5. [FJOI2015]火星商店问题

    [FJOI2015]火星商店问题 神仙线段树分治...不过我不会. 这题用线段树套可持久化Trie还是能写的. 常数有点大,洛谷垫底水平. // luogu-judger-enable-o2 #inc ...

  6. 【LG4585】[FJOI2015]火星商店问题

    [LG4585][FJOI2015]火星商店问题 题面 bzoj权限题 洛谷 \(Notice:\) 关于题面的几个比较坑的地方: "一天"不是一个操作,而是有0操作就相当于一天开 ...

  7. [FJOI2015]火星商店问题(线段树分治,可持久化,Trie树)

    [FJOI2015]火星商店问题 前天考了到线段树分治模板题,全场都切了,就我不会QAQ 于是切题无数的Tyher巨巨就告诉我:"你可以去看看火星商店问题,看了你就会了." 第一道 ...

  8. 【题解】P4585 [FJOI2015]火星商店问题(线段树套Trie树)

    [题解]P4585 [FJOI2015]火星商店问题(线段树套Trie树) 语文没学好不要写省选题面!!!! 题目大意: 有\(n\)个集合,每个集合有个任意时刻都可用的初始元素.现在有\(m\)个操 ...

  9. 【洛谷】P4585 [FJOI2015]火星商店问题

    题解 题目太丧,OJ太没有良心,我永远喜欢LOJ! (TLE报成RE,垃圾洛谷,我永远喜欢LOJ) 好的,平复一下我debug了一上午崩溃的心态= =,写一写这道题的题解 把所有限制去掉,给出一个值, ...

随机推荐

  1. crash:EXC_ARM_DA_ALIGN(关于内存对齐,memcpy)

    crash:EXC_ARM_DA_ALIGN(关于内存对齐,memcpy) 问题描述 在iOS game开发时做内存拷贝时出现了 crash:EXC_ARM_DA_ALIGN,debug版本不会出现, ...

  2. JS日期转换

    用js将从后台得到的时间戳(毫秒数)转换为想要的日期格式 得到后台从数据库中拿到的数据我们希望格式是 2016年10月25日 17时37分30秒 或者 2016/10/25 17:37:30 然而我们 ...

  3. poj3984迷宫问题(dfs+stack)

    迷宫问题 Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 35426   Accepted: 20088 Descriptio ...

  4. 程序迭代时测试操作的要点(后端&前端)

    今晚直播课内容简介,视频可点击链接免费听 <程序迭代时测试操作的要点(后端&前端)> ===== 1:迭代时后台涉及的操作有哪些?如何进行 a.更新war包:用于访问web\app ...

  5. 搭建redis集群的过程中遇到的问题

    1.GCC没有安装或版本不对 报错信息如下 CC adlist.o /bin/sh: cc: command not found make[1]: *** [adlist.o] Error 127 m ...

  6. 【system.file】使用说明

    对象:system.file 说明:提供一系列针对文件操作的方法. 注意:参数中的filePath 均为相对网站根目录路径 目录: 方法 返回 说明 system.file.exists(filePa ...

  7. 【shell 练习5】编写简单的多级菜单

    一.简单的多级菜单 [root@web129 ~]# cat menu.sh #!/bin/bash #shell菜单演示 function menu() { echo -e `date` cat & ...

  8. 机器学习(四)正则化与过拟合问题 Regularization / The Problem of Overfitting

    文章内容均来自斯坦福大学的Andrew Ng教授讲解的Machine Learning课程,本文是针对该课程的个人学习笔记,如有疏漏,请以原课程所讲述内容为准.感谢博主Rachel Zhang 的个人 ...

  9. Linux error:No space left on device

    一台Oracle数据库服务器在关机重启后,Oracle监听无法启动,提示错误 Linux error:no space left on device 提示可知:问题是出在磁盘空间不足 但是初步查看分区 ...

  10. vue学习笔记(三):vue-cli脚手架搭建

    一:安装vue-cli脚手架: 1:为了确保你的node版本在4.*以上,输入 node -v 查看本机node版本,低于4请更新. 2:输入:  npm install -g vue-cli     ...