POJ2777 线段树区间染色问题

Posted dongdong25800

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了POJ2777 线段树区间染色问题相关的知识,希望对你有一定的参考价值。

 

 

题意:给L长度的木板,给T种颜色,给O个操作,每次可以选择一段区间染色,或查询一个区间的颜色种类

思路:用线段树叶节点记录颜色所代表的数字,父节点为-1表示两个子节点颜色不相同,>0时的数字代表子节点全为这个数字对应颜色。

#include <iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
#include<cmath>
using namespace std;

const int maxn=1e5+10;
int a[maxn];
int l,t,o;
int vis[35];
struct note

    int left,right,sum,lazy;
    void up(int val)
    
        sum=val;
        lazy=val;
    
 tree[maxn*4];
void pushup(int id)

    if(tree[id<<1].sum==-1||tree[id<<1|1].sum==-1)
        tree[id].sum=-1;
    else if(tree[id<<1].sum==tree[id<<1|1].sum)
        tree[id].sum=tree[id<<1].sum;
    else
        tree[id].sum=-1;

void pushdown(int id)

    if(tree[id].lazy)
    
        tree[id<<1].up(tree[id].lazy);
        tree[id<<1|1].up(tree[id].lazy);
        tree[id].lazy=0;
    


void build(int id,int l,int r)

    tree[id].left=l;
    tree[id].right=r;
    if(l==r)
        tree[id].sum=1;
    else
    
        int mid=(l+r)/2;
        build(id<<1,l,mid);
        build(id<<1|1,mid+1,r);
        pushup(id);
    

void query(int id,int l,int r)

    if(tree[id].sum!=-1)
    
        vis[tree[id].sum]=1;
        return;
    
//    pushdown(id);
    int mid=(tree[id].left+tree[id].right)/2;
    if(l<=mid) query(id<<1,l,r);
    if(r>mid) query(id<<1|1,l,r);

void update(int id,int l,int r,int val)

    if(l<=tree[id].left&&tree[id].right<=r)
    
        tree[id].up(val);
        return;
    
    pushdown(id);
    int mid=(tree[id].left+tree[id].right)/2;
    if(l<=mid) update(id<<1,l,r,val);
    if(r>mid) update(id<<1|1,l,r,val);
    pushup(id);



int main()

    scanf("%d%d%d",&l,&t,&o);
    build(1,1,l);
    for(int i=1; i<=o; i++)
    
        char op;
        getchar();
        scanf("%c",&op);
        if(op==C)
        
            int l,r,color;
            scanf("%d%d%d",&l,&r,&color);
            update(1,l,r,color);
        
        else
        
            int l,r;
            scanf("%d%d",&l,&r);
            memset(vis,0,sizeof(vis));
            query(1,l,r);
            int ans=0;
            for(int i=1; i<=30; i++)
            
                if(vis[i])
                    ans++;
            
            printf("%d\n",ans);
        
    

 

以上是关于POJ2777 线段树区间染色问题的主要内容,如果未能解决你的问题,请参考以下文章

[日常摸鱼][poj2777]Count Color-线段树

POJ 2777 线段树

poj-2777线段树刷题

poj2777(线段树)

Count Color (线段树区间染色?二进制状态压缩)

pku 2777(经典线段树染色问题)