zoukankan      html  css  js  c++  java
  • bzoj4571 [Scoi2016]美味

    Description

    一家餐厅有 n 道菜,编号 1...n ,大家对第 i 道菜的评价值为 ai(1≤i≤n)。有 m 位顾客,第 i 位顾客的期
    望值为 bi,而他的偏好值为 xi 。因此,第 i 位顾客认为第 j 道菜的美味度为 bi XOR (aj+xi),XOR 表示异或
    运算。第 i 位顾客希望从这些菜中挑出他认为最美味的菜,即美味值最大的菜,但由于价格等因素,他只能从第 
    li 道到第 ri 道中选择。请你帮助他们找出最美味的菜。

    Input

    第1行,两个整数,n,m,表示菜品数和顾客数。
    第2行,n个整数,a1,a2,...,an,表示每道菜的评价值。
    第3至m+2行,每行4个整数,b,x,l,r,表示该位顾客的期望值,偏好值,和可以选择菜品区间。
    1≤n≤2×10^5,0≤ai,bi,xi<10^5,1≤li≤ri≤n(1≤i≤m);1≤m≤10^5

    Output

     输出 m 行,每行 1 个整数,ymax ,表示该位顾客选择的最美味的菜的美味值。

    Sample Input

    4 4
    1 2 3 4
    1 4 1 4
    2 3 2 3
    3 2 3 3
    4 1 2 4

    Sample Output

    9
    7
    6
    7

    正解:主席树。

    其实并不难,应该想得出的,但是我真的好蠢。。可能今天状态不好吧。。

    如果没有加数,那么就是裸的可持久化trie树,但是有一个加法,那么trie树就是乱搞了。

    我们从高到低考虑每一位能否取最优值。设j是当前位,如果j这位能取的话,那么当前的期望ans就是[ans,(ans|((1<<j)-1))](这个要仔细想想才能想通),ans的下界就是更高位上已经得到的ans再加上这一位的期望(0 or 1)。只要找ans-x到(ans|((1<<j)-1))-x上有没有数。那么我们就直接在主席树上找这个区间有没有数就行了。

     1 //It is made by wfj_2048~
     2 #include <algorithm>
     3 #include <iostream>
     4 #include <complex>
     5 #include <cstring>
     6 #include <cstdlib>
     7 #include <cstdio>
     8 #include <vector>
     9 #include <cmath>
    10 #include <queue>
    11 #include <stack>
    12 #include <map>
    13 #include <set>
    14 #define inf (1<<30)
    15 #define NN (262144)
    16 #define N (200010)
    17 #define il inline
    18 #define RG register
    19 #define ll long long
    20 #define File(s) freopen(s".in","r",stdin),freopen(s".out","w",stdout)
    21 
    22 using namespace std;
    23 
    24 int sum[20*N],ls[20*N],rs[20*N],rt[N],a[N],n,m,sz,ans;
    25 
    26 il int gi(){
    27     RG int x=0,q=1; RG char ch=getchar(); while ((ch<'0' || ch>'9') && ch!='-') ch=getchar();
    28     if (ch=='-') q=-1,ch=getchar(); while (ch>='0' && ch<='9') x=x*10+ch-48,ch=getchar(); return q*x;
    29 }
    30 
    31 il void insert(RG int x,RG int &y,RG int l,RG int r,RG int v){
    32     sum[y=++sz]=sum[x]+1,ls[y]=ls[x],rs[y]=rs[x]; if (l==r) return; RG int mid=(l+r)>>1;
    33     v<=mid ? insert(ls[x],ls[y],l,mid,v) : insert(rs[x],rs[y],mid+1,r,v);
    34 }
    35 
    36 il int query(RG int x,RG int y,RG int l,RG int r,RG int xl,RG int xr){
    37     if (xl<=l && r<=xr) return sum[y]-sum[x]>0; RG int mid=(l+r)>>1;
    38     if (xr<=mid) return query(ls[x],ls[y],l,mid,xl,xr);
    39     else if (xl>mid) return query(rs[x],rs[y],mid+1,r,xl,xr);
    40     else return query(ls[x],ls[y],l,mid,xl,mid)|query(rs[x],rs[y],mid+1,r,mid+1,xr);
    41 }
    42 
    43 il void work(){
    44     n=gi(),m=gi();
    45     for (RG int i=1;i<=n;++i) a[i]=gi(),insert(rt[i-1],rt[i],0,NN,a[i]);
    46     for (RG int i=1;i<=m;++i){
    47     RG int b=gi(),x=gi(),l=gi(),r=gi(); ans=0;
    48     for (RG int j=17;j>=0;--j){
    49         if (!(b&(1<<j))) ans^=1<<j;
    50         RG int L=max(ans-x,0),R=(ans|((1<<j)-1))-x;
    51         if (R<0 || !query(rt[l-1],rt[r],0,NN,L,R)) ans^=1<<j;
    52     }
    53     printf("%d
    ",ans^b);
    54     }
    55     return;
    56 }
    57 
    58 int main(){
    59     File("delicious");
    60     work();
    61     return 0;
    62 }
  • 相关阅读:
    网络基础
    python之bootstrap(组件,SweetAlert插件)
    python之网页小图标的使用
    python之bootstrap(基本)
    python之JQuery(批量操作,监听按键)
    python之JQuery(文档操作,事件委托,事件冒泡)
    python之JQuery(动画点赞实例)
    python之JQuery(hover,input值动态变化的实现)
    Less-1
    python100例 21-30
  • 原文地址:https://www.cnblogs.com/wfj2048/p/6485374.html
Copyright © 2011-2022 走看看