zoukankan      html  css  js  c++  java
  • bzoj3262: 陌上花开(CDQ+树状数组处理三维偏序问题)

    题目链接:https://www.lydsy.com/JudgeOnline/problem.php?id=3262

    题目大意:中文题目

    具体思路:CDQ可以处理的问题,一共有三维空间,对于第一维我们直接按照从小到大排序就可以了,然后就开始处理第二维,第二维的话我们通过cdq来维护,然后第三维通过树状数组维护就可以了。

    刚开始做CDQ的问题,个人觉得CDQ处理的就是把一整个大的问题转换成多个子问题进行求解,然后很重要的一个的地方就是解决前面一个子问题对后面的问题的影响。

    AC代码:

     1 #include<iostream>
     2 #include<stack>
     3 #include<stdio.h>
     4 #include<cmath>
     5 #include<algorithm>
     6 using namespace std;
     7 # define ll long long
     8 # define inf 0x3f3f3f3f
     9 const int maxn = 2e5+100;
    10 struct node{
    11 int x,y,z;
    12 int ans,cnt;
    13 }q[maxn];
    14 int maxstate;
    15 bool cmp1(node t1,node t2){
    16 if(t1.x!=t2.x)return t1.x<t2.x;
    17 if(t1.y!=t2.y)return t1.y<t2.y;
    18 return t1.z<t2.z;
    19 }
    20 bool cmp2(node t1,node t2){
    21 if(t1.y!=t2.y)return t1.y<t2.y;
    22 return t1.z<t2.z;
    23 }//注意两个cmp的不同,对于第一个cmp我们只是初始的状态,但是对于第二个cmp,我们处理的是x已经排好的前提下了,如果这个时候再对q进行排序的话,会打乱y的正常顺序。
    24 int vis[maxn],tree[maxn<<2];
    25 int lowbit(int x){return x&(-x);}
    26 void update(int x,int val){
    27 while(x<=maxstate){
    28 tree[x]+=val;
    29 x+=lowbit(x);
    30 }
    31 }
    32 int  ask(int x){
    33 int ans=0;
    34 while(x){
    35 ans+=tree[x];
    36 x-=lowbit(x);
    37 }
    38 return ans;
    39 }
    40 void cdq(int l,int r){
    41 if(l==r){
    42 q[l].ans+=q[l].cnt-1;
    43 return ;
    44 }
    45 int mid=(l+r)>>1;
    46 cdq(l,mid);
    47 cdq(mid+1,r);
    48 sort(q+l,q+mid+1,cmp2);
    49 sort(q+mid+1,q+r+1,cmp2);
    50 int tmp=l;
    51 for(int i=mid+1;i<=r;i++){
    52 while(tmp<=mid&&q[i].y>=q[tmp].y){
    53 update(q[tmp].z,q[tmp].cnt),tmp++;
    54 }
    55 q[i].ans+=ask(q[i].z);
    56 }
    57 for(int i=l;i<tmp;i++){
    58 update(q[i].z,-q[i].cnt);
    59 }//消除前面一个子问题对后面的子问题的影响
    60 }
    61 int main(){
    62     //freopen("hqx.in","r",stdin);
    63 int n;
    64 scanf("%d %d",&n,&maxstate);
    65 for(int i=1;i<=n;i++){
    66 scanf("%d %d %d",&q[i].x,&q[i].y,&q[i].z);
    67 q[i].cnt=1;
    68 q[i].ans=0;
    69 }
    70 int tot=0;
    71 sort(q+1,q+n+1,cmp1);
    72 for(int i=1;i<=n;i++){
    73 if(i!=1&&q[i].x==q[tot].x&&q[i].y==q[tot].y&&q[i].z==q[tot].z)q[tot].cnt++;
    74 else q[++tot]=q[i];
    75 }
    76 cdq(1,tot);
    77 for(int i=1;i<=tot;i++){
    78 vis[q[i].ans]+=q[i].cnt;
    79 }
    80 for(int i=0;i<n;i++){
    81 printf("%d
    ",vis[i]);
    82 }
    83 return 0;
    84 }
  • 相关阅读:
    做好最后的1%
    南海城市大脑二期测试的思考
    职场动物进化手册
    搜索框测试用例
    三月版三一金票需求测试总结
    “魔鬼”隐藏在细节中
    java----jdbcTemplate
    内网隧道与SOCKS代理思路总结
    一些免杀方法测试
    JavaScript 关于闭包、同步、异步问题
  • 原文地址:https://www.cnblogs.com/letlifestop/p/10456288.html
Copyright © 2011-2022 走看看