zoukankan      html  css  js  c++  java
  • 【HDU1199】 离散化线段树

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1199

    题目大意: 一段长度未知的线段,一种操作:a b c ,表示区间[a,b]要涂的颜色,c=w涂白色,c=b涂黑色,问你最长的白色区间段时多长。

    解题思路:

                就快去南京邀请赛了,最近做题超没状态,CF rating一直掉,这么简单的线段树离散化居然搞了我一个晚上,纠结。

                开始用线段树区间合并的方法做,WA到死,换个写法,又WA到死,没处理好边界问题。

                这题用普通的离散化没用,藐视这种离散化第一次遇见,以前的离散化要么就是点化点,线段化点,这题不一样,是点化线段,一不小心处理不好就WA了。

    点化线段我利用的是左闭右开,即对于一段区间[a,b],转化成区间[a,b+1),接下来就是把所有端点当做简单的离散化处理了,然后运用线段树成段更新操作处理就好了。

    View Code
      1 #include <iostream>
      2 #include <cstdio>
      3 #include <cstring>
      4 #include <algorithm>
      5 using namespace std;
      6 
      7 #define lz 2*u,l,mid
      8 #define rz 2*u+1,mid,r   ///注意:这里是点化为线段(左闭右开)
      9 const int maxn=5555;
     10 const int oo=0x3fffffff;
     11 int flag[4*maxn], color[maxn];
     12 int X[maxn];
     13 
     14 struct Node
     15 {
     16     int lx, rx, s;
     17     Node(){}
     18     Node(int lx_, int rx_, int s_)
     19     {
     20         lx=lx_, rx=rx_, s=s_;
     21     }
     22 }line[maxn];
     23 
     24 void push_down(int u, int l, int r)
     25 {
     26     if(flag[u]==-1) return ;
     27     else
     28     {
     29         flag[2*u]=flag[2*u+1]=flag[u];
     30         flag[u]=-1;
     31     }
     32 }
     33 
     34 void Update(int u, int l, int r, int tl, int tr, int c)
     35 {
     36     if(tl>=tr) return ; ///这里要注意了
     37     if(tl<=l&&r<=tr)
     38     {
     39         flag[u]=c;
     40         return ;
     41     }
     42     push_down(u,l,r);
     43     int mid=(l+r)>>1;
     44     if(tr<=mid) Update(lz,tl,tr,c);
     45     else if(tl>mid) Update(rz,tl,tr,c);
     46     else
     47     {
     48         Update(lz,tl,mid,c);
     49         Update(rz,mid,tr,c);
     50     }
     51 }
     52 
     53 void Query(int u, int l, int r)
     54 {
     55     if(l>=r) return ; ///!!!
     56     if(flag[u]!=-1)
     57     {
     58         for(int i=l; i<r; i++) color[i]=flag[u];  ///右端点不标记
     59         return ;
     60     }
     61     push_down(u,l,r);
     62     int mid=(l+r)>>1;
     63     Query(lz);
     64     Query(rz);
     65 }
     66 
     67 int find(int tmp, int n)
     68 {
     69     int l=1, r=n, mid;
     70     while(l<=r)
     71     {
     72         mid=(l+r)>>1;
     73         if(X[mid]==tmp) return mid;
     74         else if(X[mid]<tmp) l=mid+1;
     75         else r=mid-1;
     76     }
     77 }
     78 
     79 int main()
     80 {
     81     int n, x, y, c;
     82     char ch[3];
     83     while(~scanf("%d",&n))
     84     {
     85         int num=0;
     86         for(int i=0; i<n; i++)
     87         {
     88             scanf("%d%d%s",&x,&y,ch);
     89             if(*ch=='w') c=1;
     90             else c=0;
     91             line[i]=Node(x,y+1,c);
     92             X[++num]=x;
     93             X[++num]=y+1;
     94         }
     95         sort(X+1,X+num+1);
     96         int ep=1;
     97         for(int i=2; i<=num; i++)
     98             if(X[ep]!=X[i]) X[++ep]=X[i];
     99         memset(color,0,sizeof(color));
    100         memset(flag,-1,sizeof(flag));
    101         for(int i=0; i<n; i++)
    102         {
    103             int lx=find(line[i].lx,ep);
    104             int rx=find(line[i].rx,ep);
    105             Update(1,1,ep+1,lx,rx,line[i].s);
    106         }
    107         Query(1,1,ep+1);
    108         int s=0, d=0, ts, td;
    109         for(int i=1; i<=ep; i++)
    110         {
    111               if(color[i]!=1) continue;
    112               ts=X[i];
    113               while(color[i]==1) i++;
    114               if(i>ep) break;
    115               td=X[i];
    116               if(td-ts>d-s)
    117               {
    118                   s=ts;
    119                   d=td;
    120               }
    121         }
    122         if(s==d) puts("Oh, my god");
    123         else printf("%d %d\n",s, d-1);
    124     }
    125     return 0;
    126 }
  • 相关阅读:
    matlab矩阵中如何去掉重复的行;如何找到相同的行,并找到其位置
    Coursera 机器学习 第9章(下) Recommender Systems 学习笔记
    机器学习基石笔记1——在何时可以使用机器学习(1)
    Coursera 机器学习 第9章(上) Anomaly Detection 学习笔记
    matlab安装过程的被要求的配置程序
    jdk环境变量配置
    Coursera 机器学习 第8章(下) Dimensionality Reduction 学习笔记
    Coursera 机器学习 第8章(上) Unsupervised Learning 学习笔记
    Coursera 机器学习 第7章 Support Vector Machines 学习笔记
    linux服务器---squid限制
  • 原文地址:https://www.cnblogs.com/kane0526/p/3048274.html
Copyright © 2011-2022 走看看