zoukankan      html  css  js  c++  java
  • Luogu P1558 色板游戏

    题目传送门

    此解法超级暴力。洛谷最优解倒数……


    因为为这道题只有(30)种颜色,所以我们可以用30颗线段树来分别维护每种颜色。
    涂颜色就将对应颜色的线段树区间染色成(1),其他的染成(0)
    统计颜色就把线段树都枚举一遍,统计在这个区间上有(1)的线段树数量

    然而正解是压位线段树

    思路好想,理论时间复杂度也能过,就是常数大,在洛谷不开(O_2)过不去……

    #include<iostream>
    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #define ls p<<1
    #define rs p<<1|1
    #define mid ((l+r)>>1)
    using namespace std;
    struct zzz{  //线段树
        int tree[100010<<2],tag[100010<<2];
        void build(int l,int r,int p){
            if(l==r){
                tree[p]=1; return ;
            }
            build(l,mid,ls); build(mid+1,r,rs);
            tree[p]=tree[ls]+tree[rs];
        }
        inline void down(int l,int r,int p){
            if(tag[p]==-1) return ;
            tree[ls]=(mid-l+1)*tag[p];
            tree[rs]=(r-mid)*tag[p];
            tag[ls]=tag[p]; tag[rs]=tag[p]; tag[p]=-1;
        }
        void update(int l,int r,int p,int nl,int nr,int k){
            if(l>=nl&&r<=nr){
                tree[p]=k*(r-l+1); tag[p]=k;
                return ;
            }
            down(l,r,p);
            if(nl<=mid) update(l,mid,ls,nl,nr,k);
            if(nr>mid) update(mid+1,r,rs,nl,nr,k);
            tree[p]=tree[ls]+tree[rs];
        }
        int query(int l,int r,int p,int nl,int nr){
            int ans=0;
            if(l>=nl&&r<=nr) return tree[p];
            down(l,r,p);
            if(nl<=mid) ans+=query(l,mid,ls,nl,nr);
            if(nr>mid) ans+=query(mid+1,r,rs,nl,nr);
            return ans;
        }
    }color[31];  //三十颗线段树
    inline int read(){
        int k=0,f=1; char c=getchar();
        for(;c<'0'||c>'9';c=getchar())
          if(f=='-') f=-1;
        for(;c>='0'&&c<='9';c=getchar())
          k=k*10+c-48;
        return k*f;
    }
    inline char read_c(){
        char c=getchar();
        for(;c<'A'||c>'Z';) c=getchar();
        for(;c>='A'&&c<='Z';)
        return c;
    }
    int main(){
        int n=read(),t=read(),m=read();
        for(int i=1;i<=t;i++) memset(color[i].tag,-1,sizeof(color[i].tag));
        color[1].build(1,n,1);  //初始颜色全为1
        for(int i=1;i<=m;i++){
            char c=read_c();
            if(c=='C'){
                int x=read(),y=read(),z=read();
                if(x>y) x^=y^=x^=y; //x^=y^=x^=y等价于swap(x,y)
                for(int i=1;i<=t;i++){  //涂颜色
                    if(i==z) color[i].update(1,n,1,x,y,1);
                    else color[i].update(1,n,1,x,y,0);
                }
            }
            else{
                int x=read(),y=read(),anss=0;
                if(x>y) x^=y^=x^=y;
                for(int i=1;i<=t;i++){  //统计颜色
                    if(color[i].query(1,n,1,x,y)) ++anss;
                }
                printf("%d
    ",anss);
            }
        }
        return 0;
    }
    

    第十个测试点刚好卡过
    卡过

  • 相关阅读:
    网页动画
    浮动
    定位
    盒子模型
    表单
    2017年07月05号课堂笔记
    2017年07月07号课堂笔记
    2017年07月03号课堂笔记
    2017年06月30号课堂笔记
    2017年06月28号课堂笔记
  • 原文地址:https://www.cnblogs.com/morslin/p/11854879.html
Copyright © 2011-2022 走看看