【POJ No. 2777】 颜色统计 Count Color

news2024/9/25 17:19:32

【POJ No. 2777】 颜色统计 Count Color

北大OJ 题目地址

在这里插入图片描述

【题意】

有一个长L 厘米的电路板,可以将板均分为L 段(1~L ),每段长1厘米。现在给电路板上色,每段只有一种颜色。可以在电路板上执行两种操作:①C a b c ,从a 段到b 段涂色为c ;②P a b ,输出a 段和b 段之间不同颜色的数量(包括a 、b),颜色编号为1~T 。

开始时,在电路板上涂有颜色1。

【输入输出】

输入:

第1行包含3个整数L (1≤L ≤105 )、T (1≤T ≤30)和O (1≤O ≤105 ,表示操作次数)。接下来的O 行,每行都包含C a b c 或P a b (a 、b 、c 是整数,a 可以大于b )。

输出:

按顺序单行输出操作结果。

【样例】

在这里插入图片描述

【思路分析】

根据输入样例,长度L =2,颜色数T =2,操作次数O =4,初始时均为1号色。

在这里插入图片描述

① C 1 1 2:将1-1段涂2号色。

在这里插入图片描述

② P 1 2:统计1-2段的颜色数,输出颜色数2。

③ C 2 2 2:将2-2段涂2号色。

在这里插入图片描述

④ P 1 2:统计1-2段的颜色数,输出颜色数1。

这道题包括区间修改、区间查询,可以用线段树解决。

由于这题的区间查询只需统计该区间的颜色数,因此并不需要将区间内的所有颜色求和。

【 算法设计】

① 创建线段树,树根的颜色为1(相当于懒标记),其他节点的颜色为0。

② 查询[l , r ]区间的颜色数。若树根rt颜色不为0,则ans[tree[rt].color]=true,返回;否则递归查询左右子树。统计所有颜色k ,若ans[k ]为真,则tot++,最后输出tot即可。

③ 更新[l , r ]区间的颜色为c 。若树根正好为该区间,则将根节点的颜色修改为c ,tree[rt].color=c ,返回;否则树根颜色下传(左右子树等于根的颜色,将根的颜色修改为0);递归更新左右子树;返回时颜色统一(若左右子树颜色相同,则将树根的颜色也修改为该颜色)。

【本题秘诀】

  • 查询时,遇到第1个颜色非0节点,标记后返回,否则递归查询左右子树;
  • 更新时,将区间的颜色号修改为c ,在查找过程中颜色下传,回退时颜色统一。

【举个栗子】

① 创建线段树,树根的颜色为1(相当于懒标记),其他节点的颜色为0。

在这里插入图片描述

② P 1 2:统计1-2段的颜色数,因为树根[1, 10]为1号色,不为0,所以令ans[1]=true,返回;统计后1-2段的颜色数为1。

③ C 4 6 2:将4-6段涂2号色。首先搜索[4, 5]、[6, 6]区间,在搜索过程中若颜色不为0,则将其作为懒标记下传。将当前节点的懒标记下传给左右子节点,当前节点的颜色为0。

在这里插入图片描述

将[4, 5]、[6, 6]区间的颜色修改为2,然后返回,在返回过程中若当前节点的左右子树颜色相同,则当前节点的颜色和它们一致。

在这里插入图片描述

④ P 5 8:统计5-8段的颜色数,因为树根[1, 10]的颜色为0,所以递归查询左右子树,[4, 5]的颜色为2,令ans[2]=true,返回;[6, 6]的颜色为2,令ans[2]=true,返回;[7, 7]的颜色为1,令ans[1]=true,返回;[8, 8]的颜色为1,令ans[1]=true,返回。统计后5-8段的颜色数为2。

注意:查询时遇到第一个颜色不为0的节点才会返回。

在这里插入图片描述

⑤ C 5 9 5:将5-9段涂1号色。首先搜索[5, 5]、[6, 8]、[9,9]区间。在搜索过程中若颜色不为0,则将其作为懒标记下传。

在这里插入图片描述

将[5, 5]、[6, 8]、[9, 9]区间的颜色修改为1,然后返回。返回时[9, 10]、[6, 10]区间左右子树的颜色相同,颜色修改与其左右子树一致,均为1。

在这里插入图片描述

⑥ P 6 7:统计6-7段的颜色数,因为树根[1, 10]的颜色为0,所以递归查询右子树,[6, 10]的颜色为1,令ans[1]=true,返回。统计后6-7段的颜色数为1。

【算法实现】

#include<cstdio>
#include<cstring>
#define lc ((rt)<<1)
#define rc ((rt)<<1|1)
#define maxn 100010

int ans[50];

struct node{
    int l,r,color;
}tree[maxn*4];

void build(int rt,int l,int r){//创建线段树 
    tree[rt].l=l; tree[rt].r=r;
	if(rt!=1) tree[rt].color=0;
    if(l==r) return;
    int mid=(l+r)>>1;
    build(lc,l,mid); build(rc,mid+1,r);
}

void lift_up(int rt){//颜色统一 
    if(tree[lc].color==tree[rc].color)
		tree[rt].color=tree[lc].color;
}

void push_down(int rt){//颜色下传 
    if(tree[rt].color){
        tree[lc].color=tree[rc].color=tree[rt].color;
        tree[rt].color=0;
    }
}

void modify(int rt,int l,int r,int c){//修改 
    if (tree[rt].l==l&&tree[rt].r==r){
        tree[rt].color=c;
        return;
    }
    push_down(rt);
    int mid=(tree[rt].l+tree[rt].r)>>1;
    if(r<=mid) modify(lc,l,r,c);
    else if(l>mid) modify(rc,l,r,c);
	else {modify(lc,l,mid,c);modify(rc,mid+1,r,c);}
    lift_up(rt);
}

void query(int rt,int l,int r){//查询 
    if(tree[rt].color){
        ans[tree[rt].color]=true;
        return;
    }
    int mid=(tree[rt].l+tree[rt].r)>>1;;
    if(r<=mid) query(lc,l,r);
    else if(l>mid) query(rc,l,r);
    else {query(lc,l,mid);query(rc,mid+1,r);}
}

int main(){
	
    int n,t,o;
    scanf("%d%d%d",&n,&t,&o);
	
    tree[1].color=1;
    build(1,1,n);
    for(int i=0;i<o;i++){
        char ch;
        scanf("\n%c",&ch);
        int l,r;
        if(ch=='C'){
            int c;
            scanf("%d%d%d",&l,&r,&c);
            modify(1,l,r,c);
        }
        else{
            memset(ans,0,sizeof(ans));
            scanf("%d%d",&l,&r);
            query(1,l,r);
            int tot=0;
            for(int k=1;k<=t;k++)
				if(ans[k])
					tot++;
            printf("%d\n",tot);
        }
    }
	
    return 0;
}

在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/56541.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

Qt扫盲-Assistant 助手使用总结

Qt Assistant助手 使用记录预备一、顶部菜单栏1. 快捷栏2. 文件、前往、帮助3. 查看-工具栏4. 编辑-首选项5. 书签二、侧边菜单栏1. 修改显示功能Bar2. 内容3. 索引4. 书签三、内容主体1. 结构总览 Content2. Properties3. Public Functions4. Reimplemented Public Functions5…

【JUC】并发编程学习笔记(三)

JUC并发编程八、ReentrantReadWriteLock 读写锁8.1、概述8.2、案例8.3、读写锁的降级九、BlockingQueue阻塞队列9.1、阻塞队列概述9.2、阻塞队列分类9.2.1、ArrayBlockingQueue(常用)9.2.2、LinkedBlockingQueue(常用)9.2.3、 DelayQueue9.2.4、 PriorityBlockingQueue9.2.5、 …

混合馈能悬架的设计与仿真(MATLAB)

目 录 摘 要 I Abstract II 第一章 绪论 1 1.1课题研究背景和意义 1 1.2国内外研究现状 2 1.3本文的主要研究内容 4 第二章 混合馈能悬架系统的工作原理 5 2.1混合馈能悬架系统的设计理念 5 2.2馈能系统的原理 6 2.3馈能系统的类型 6 2.4混合馈能悬架系统结构选型 8 2.5本章小结…

技术分享 | 如何确保API 的稳定性与正确性?你只需要这一招

现在&#xff0c;越来越多的 Web 应用转向了RESTful的架构&#xff0c;很多产品和应用暴露给用户的往往就是一组 REST API&#xff0c;这样有一个好处&#xff0c;用户可以根据需要&#xff0c;调用不同的 API&#xff0c;整合出自己的应用出来。从这个角度来讲&#xff0c;Web…

前端字体压缩(免费简单易上手)

场景&#xff1a;前端在开发过程中有时候要用到特殊字体&#xff0c;但如果引用网上下载好的字体&#xff0c;它们都是一个全的字体文件&#xff0c;这种字体文件里往往包含了大量你用不到的文字字符&#xff0c;从而导致你引入的字体文件大小高达1M以上&#xff0c;这会严重影…

C++08函数模板

1.自动推导类型 在C语言和C98中&#xff0c;auto 关键字用于修饰变量(自动存储的局部变量)。 在C11中&#xff0c;赋予了auto 全新的含义&#xff0c;不再用于修饰的变量&#xff0c;而是作为一个类型指示符&#xff0c;指示编译器在编译时推导auto声明的变量的数据类型。 在…

SpirngBoot<读完包你更上一层楼>

目录 一、SpringBoot概念 1.1 什么是SpringBoot 1.2 为什么要学习SpringBoot 1.3 SpringBoot的特点 1.4 总结 二、入门案例 2.1 创建工程 2.1.1 创建一个空工程 2.1.2 工程名为project_test&#xff1a; 2.1.3 设置jdk版本为1.8 2.1.4 新建一个module 2.1.5 填写项…

入职字节外包一个月,我离职了

有一种打工人的羡慕&#xff0c;叫做“大厂”。 真是年少不知大厂香&#xff0c;错把青春插稻秧。 但是&#xff0c;在深圳有一群比大厂员工更庞大的群体&#xff0c;他们顶着大厂的“名”&#xff0c;做着大厂的工作&#xff0c;还可以享受大厂的伙食&#xff0c;却没有大厂…

[附源码]计算机毕业设计springboot吾悦商城管理系统

项目运行 环境配置&#xff1a; Jdk1.8 Tomcat7.0 Mysql HBuilderX&#xff08;Webstorm也行&#xff09; Eclispe&#xff08;IntelliJ IDEA,Eclispe,MyEclispe,Sts都支持&#xff09;。 项目技术&#xff1a; SSM mybatis Maven Vue 等等组成&#xff0c;B/S模式 M…

老司机带带你,教你学会Java中又骚又暴力的“反射”技术

在Java中有这么一个很骚的技术&#xff0c;几乎贯穿了所有主流的框架&#xff0c;在所有主流框架的底层中你都可以看见它的身影&#xff0c;这个技术就是反射。关于反射&#xff0c;有很多小白会觉得很难&#xff0c;搞不清楚到底是怎么回事&#xff0c;也不知道该怎么用&#…

VS Code快速实现Git PR操作

注意&#xff1a;建议先学习git的基本操作。 安装插件 下图中红圈标记的插件都安装好。 Fork上游仓库 在网页上点击你想要fork的仓库&#xff0c;点击fork 然后该仓库就会fork到你的github账户下面&#xff0c;如下图。 现在可以在你账户下面的repo&#xff08;我们称为下…

[附源码]Python计算机毕业设计Django和vue的茶文化交流平台的设计与实现

项目运行 环境配置&#xff1a; Pychram社区版 python3.7.7 Mysql5.7 HBuilderXlist pipNavicat11Djangonodejs。 项目技术&#xff1a; django python Vue 等等组成&#xff0c;B/S模式 pychram管理等等。 环境需要 1.运行环境&#xff1a;最好是python3.7.7&#xff0c;…

Global Mapper 导出图层功能的妙用(重采样、设置文件类型、切片、按掩膜提取or裁剪……)

许多GIS软件都有导出的功能&#xff0c;但其中大部分的导出功能比较单一直接&#xff0c;仅仅是导出而已&#xff0c;或者最多可以改个导出的格式&#xff0c;改个坐标。但是Global Mapper 不一样&#xff0c;导出功能非常非常多&#xff0c;比如重采样&#xff08;可以设置重采…

Vue3框架的创建的两种种方案(第十二课)

1 VueCLi脚手架的安装 Home | Vue CLI (vuejs.org) 使用方法 | Yarn 中文文档 (bootcss.com) 3 Vite脚手架的安装 Vite | 下一代的前端工具链 4 使用的软件 Visual Studio Code webstorm64.exe IntelliJ IDEA 2022.2.3 HBuilder X 方案一 VueCLi脚手架的安装 1 创…

[附源码]计算机毕业设计在线招聘网站Springboot程序

项目运行 环境配置&#xff1a; Jdk1.8 Tomcat7.0 Mysql HBuilderX&#xff08;Webstorm也行&#xff09; Eclispe&#xff08;IntelliJ IDEA,Eclispe,MyEclispe,Sts都支持&#xff09;。 项目技术&#xff1a; SSM mybatis Maven Vue 等等组成&#xff0c;B/S模式 M…

MobileViT

还是vit系列啊 只不过这次是Apple团队出的轻量级、通用且移动友好的网络框架 论文地址&#xff1a;https://arxiv.org/pdf/2110.02178.pdf 轻量级卷积神经网络 (CNN) 是移动视觉任务的事实。他们的空间归纳偏差使他们能够在不同的视觉任务中以较少的参数学习表示。 轻量级卷积…

微服务自动化【集群搭建】

目录 搭建 etcd 集群 etcd构建自身高可用集群主要有三种形式: 1. 静态部署(前提) 2. 集群搭建 3. 集群测试 搭建 etcd 集群 etcd构建自身高可用集群主要有三种形式: 静态发现:预先已知etcd集群中有哪些节点&#xff0c; 在启动时通过--initial-cluster参数直接指定好etc…

[附源码]JAVA毕业设计互联网保险网站(系统+LW)

[附源码]JAVA毕业设计互联网保险网站&#xff08;系统LW&#xff09; 目运行 环境项配置&#xff1a; Jdk1.8 Tomcat8.5 Mysql HBuilderX&#xff08;Webstorm也行&#xff09; Eclispe&#xff08;IntelliJ IDEA,Eclispe,MyEclispe,Sts都支持&#xff09;。 项目技术&a…

JavaWeb(一)

前言 首先深入了解之前&#xff0c;先回顾一些基础知识 C/S & B/S 就比如咱们日常生活中&#xff0c;咱们说的CF是cs游戏&#xff0c;这个cs是什么意思&#xff08;年幼的我也十分痴迷CF游戏&#xff0c;过去式了 hhh&#xff09;这里的cs可不是咱们说的csgo或者cs游戏。…

Vue 官方文档2.x教程学习笔记 1 基础 1.4 模板语法 1.4.1 插值

Vue 官方文档2.x教程学习笔记 文章目录Vue 官方文档2.x教程学习笔记1 基础1.4 模板语法1.4.1 插值1 基础 1.4 模板语法 【介绍】 Vue.js 使用了基于 HTML 的模板语法&#xff0c;允许开发者声明式地将 DOM 绑定至底层 Vue 实例的数据。 所有 Vue.js 的模板都是合法的 HTML&…