• P1558 色板游戏 线段树


      

    题目背景

    阿宝上学了,今天老师拿来了一块很长的涂色板。

    题目描述

    色板长度为L,L是一个正整数,所以我们可以均匀地将它划分成L块1厘米长的小方格。并从左到右标记为1, 2, ... L。

    现在色板上只有一个颜色,老师告诉阿宝在色板上只能做两件事:

    1. "C A B C" 指在A到 B 号方格中涂上颜色 C。
    2. "P A B" 指老师的提问:A到 B号方格中有几种颜色。

    学校的颜料盒中一共有 T 种颜料。为简便起见,我们把他们标记为 1, 2, ... T. 开始时色板上原有的颜色就为1号色。 面对如此复杂的问题,阿宝向你求助,你能帮助他吗?

    输入输出格式

    输入格式:

    第一行有3个整数 L (1 <= L <= 100000), T (1 <= T <= 30) 和 O (1 <= O <= 100000)。 在这里O表示事件数。
    接下来 O 行, 每行以 "C A B C" 或 "P A B" 得形式表示所要做的事情(这里 A, B, C 为整数, 可能A> B,这样的话需要你交换A和B)

    输出格式:

    对于老师的提问,做出相应的回答。每行一个整数。

    输入输出样例

    输入样例#1: 复制
    2 2 4
    C 1 1 2
    P 1 2
    C 2 2 2
    P 1 2
    输出样例#1: 复制
    2
    1


    只有取答案的时候是加异或
    #include<bits/stdc++.h>
    using namespace std;
    //input by bxd
    #define rep(i,a,b) for(int i=(a);i<=(b);i++)
    #define repp(i,a,b) for(int i=(a);i>=(b);--i)
    #define RI(n) scanf("%d",&(n))
    #define RII(n,m) scanf("%d%d",&n,&m)
    #define RIII(n,m,k) scanf("%d%d%d",&n,&m,&k)
    #define RS(s) scanf("%s",s);
    #define ll long long
    #define pb push_back
    #define CLR(A,v)  memset(A,v,sizeof A)
    //////////////////////////////////
    #define inf 0x3f3f3f3f
    #define lson l,m,pos<<1
    #define rson m+1,r,pos<<1|1
    const int N=100000;
    
    int sum[N<<2],col[N<<2],n,m,t,cnt,a,b,k,c;
    
    int getans(int x)
    {
        int cnt=0;
        while(x)
        {
            if(x&1)cnt++;
            x>>=1;
        }
        return cnt;
    }
    void up(int pos)
    {
        sum[pos]=(sum[pos<<1]|sum[pos<<1|1]);
    }
    void build(int l,int r,int pos)
    {
        col[pos]=0;
        if(l==r){sum[pos]=1; return ;}
        int m=(l+r)>>1;
        build(lson);build(rson);
        up(pos);
    }
    void down(int pos)
    {
        if(col[pos])
        {
            col[pos<<1]=col[pos];
            col[pos<<1|1]=col[pos];
            sum[pos<<1]=col[pos];
            sum[pos<<1|1]=col[pos];
            col[pos]=0;
        }
    }
    void update(int L,int R,int v,int l,int r,int pos)
    {
        if(L<=l&&r<=R)
        {
            col[pos]=(1<<(v-1));
            sum[pos]=(1<<(v-1));
            return ;
        }
        down(pos);
        int m=(l+r)>>1;
        if(L<=m)update(L,R,v,lson);
        if(R>m)update(L,R,v,rson);
        up(pos);
    }
    
    void query(int L,int R,int l,int r,int pos)
    {
        if(L<=l&&r<=R)
        {
            cnt|=sum[pos];
            return ;
        }
        int m=(l+r)>>1;
        down(pos);
        if(L<=m)query(L,R,lson);
        if(R>m)query(L,R,rson);
        up(pos);
    }
    
    char s[3];
    int main()
    {
        RIII(n,t,k);
        build(1,n,1);
    
        while(k--)
        {
            RS(s);
            if(s[0]=='C')
            {
                RIII(a,b,c);if(a>b)swap(a,b);
                update(a,b,c,1,n,1);
            }
            else
            {
                cnt=0;
                RII(a,b);if(a>b)swap(a,b);
                query(a,b,1,n,1);
                cout<<getans(cnt)<<endl;
            }
        }
        return 0;
    }
    View Code






  • 相关阅读:
    Linux中权限管理之文件特殊权限
    Linux中权限管理之ACL权限
    Linux用户管理命令
    【并发编程】实现多线程的几种方式
    “数据中台”的再思考
    软件工程六大设计原则总结,案例演示
    你必须要知道的移动端开发知识
    【搞定面试官】你还在用Executors来创建线程池?会有什么问题呢?
    EasyCode实现数据库到Swagger全自动化
    【Java实例】使用Thumbnailator生成缩略图(缩放、旋转、裁剪、水印)
  • 原文地址:https://www.cnblogs.com/bxd123/p/10928131.html
Copyright © 2020-2023  润新知