hdu4288--Coder--线段树--离线处理+离散化+想法!

2024-06-12 12:18

本文主要是介绍hdu4288--Coder--线段树--离线处理+离散化+想法!,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

做过的线段树做到现在收获最大的一题~~~


以后还要多做几遍~~~


学会了左加右减的位移思想,


学会了离线处理数据,


学会了用lower_bound或者upper_bound寻找hash中某个数值所在的数组下标~~


整道题的思路和注释都写在代码里了。


//HDU 4288 线段树离线+离散化
#include <cstdio>
#include <cstring>
#include <algorithm>
#include <iostream>
using namespace std;
typedef long long ll;
const int maxnum=1e5+10;char op[maxnum][5];
int  num[maxnum];
int hash[maxnum];struct Node
{int l,r;//int ll,rr;本来想写实际ll和rr的,后来发现其实可以通过upper_bound找到插入元素的index,就不必每次都去考虑实际大小来进行插入了ll sum[5];//分别对应余数为0,1,2,3,4的情况int cnt;//结点对应的区间内实际有多少个数
}tree[maxnum*3];void build(int l,int r,int root)
{tree[root].l=l,tree[root].r=r,tree[root].cnt=0;for(int i=0;i<5;++i)tree[root].sum[i]=0;if(l==r) return;int mid=(l+r)>>1;build(l,mid,root<<1);build(mid+1,r,root<<1|1);
}void update(int root,int position,int adder)
{int l=tree[root].l,r=tree[root].r;if(l==r){if(adder>0){tree[root].cnt=1;tree[root].sum[1]=hash[position];}else if(adder<0){tree[root].cnt=0;tree[root].sum[1]=0;}}else{tree[root].cnt+=adder;//这里一开始二货了。。。线段树更新时一定要考虑每次究竟要更新哪些东西。int mid=(l+r)>>1;if(position<=mid) update(root<<1,position,adder);else if(position>mid) update(root<<1|1,position,adder);for(int i=0;i<5;++i)tree[root].sum[i]=tree[root<<1].sum[i]+tree[root<<1|1].sum[(i-tree[root<<1].cnt%5+5)%5];//这里有一个左加右减的思想= =#好奇妙的说。。。。//父结点mod 5=i的值来源于左结点的值,加上右结点中 mod 5=x,中的x的值,即tree[root<<1|1].sum[x]的值。//而x=(i-tree[root<<1].cnt%5+5)%5//为什么呢,因为左结点中的起始结点前面没有数,而右结点前面有tree[root<<1].cnt个数//因而相当于把右结点向右平移cnt个单位//根据左加右减的思想,实际求的x即为i-tree[root<<1].cnt在5域下的值。}
}int main()
{//freopen("input.txt","r",stdin);int n;while(~scanf("%d",&n)){int i;int p=1,q=2;for(i=1;i<=n;++i){scanf("%s",op[i]);if(op[i][0]!='s'){scanf("%d",&num[i]);//用num数组记录每次操作存入的数hash[p++]=num[i];//hash进行离散化}}//离线处理--p;sort(hash+1,hash+p+1);for(i=2;i<=p;++i) if(hash[i]!=hash[i-1]) hash[q++]=hash[i];--q;build(1,q,1);for(int i=1;i<=n;++i){if(op[i][0]=='s') {cout<<tree[1].sum[3];printf("\n");}else{int position=lower_bound(hash+1,hash+1+q,num[i])-hash;//low_bound返回第一个大于等于value的值,记住指针范围!!!//或者写int position=upper_bound(hash+1,hash+1+q,num[i])-(hash+1);if(op[i][0]=='a') update(1,position,1);else if(op[i][0]=='d') update(1,position,-1);}}}return 0;
}


这篇关于hdu4288--Coder--线段树--离线处理+离散化+想法!的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/1054192

相关文章

SpringBoot分段处理List集合多线程批量插入数据方式

《SpringBoot分段处理List集合多线程批量插入数据方式》文章介绍如何处理大数据量List批量插入数据库的优化方案:通过拆分List并分配独立线程处理,结合Spring线程池与异步方法提升效率... 目录项目场景解决方案1.实体类2.Mapper3.spring容器注入线程池bejsan对象4.创建

PHP轻松处理千万行数据的方法详解

《PHP轻松处理千万行数据的方法详解》说到处理大数据集,PHP通常不是第一个想到的语言,但如果你曾经需要处理数百万行数据而不让服务器崩溃或内存耗尽,你就会知道PHP用对了工具有多强大,下面小编就... 目录问题的本质php 中的数据流处理:为什么必不可少生成器:内存高效的迭代方式流量控制:避免系统过载一次性

Python实现批量CSV转Excel的高性能处理方案

《Python实现批量CSV转Excel的高性能处理方案》在日常办公中,我们经常需要将CSV格式的数据转换为Excel文件,本文将介绍一个基于Python的高性能解决方案,感兴趣的小伙伴可以跟随小编一... 目录一、场景需求二、技术方案三、核心代码四、批量处理方案五、性能优化六、使用示例完整代码七、小结一、

Python中 try / except / else / finally 异常处理方法详解

《Python中try/except/else/finally异常处理方法详解》:本文主要介绍Python中try/except/else/finally异常处理方法的相关资料,涵... 目录1. 基本结构2. 各部分的作用tryexceptelsefinally3. 执行流程总结4. 常见用法(1)多个e

PHP应用中处理限流和API节流的最佳实践

《PHP应用中处理限流和API节流的最佳实践》限流和API节流对于确保Web应用程序的可靠性、安全性和可扩展性至关重要,本文将详细介绍PHP应用中处理限流和API节流的最佳实践,下面就来和小编一起学习... 目录限流的重要性在 php 中实施限流的最佳实践使用集中式存储进行状态管理(如 Redis)采用滑动

MyBatis-plus处理存储json数据过程

《MyBatis-plus处理存储json数据过程》文章介绍MyBatis-Plus3.4.21处理对象与集合的差异:对象可用内置Handler配合autoResultMap,集合需自定义处理器继承F... 目录1、如果是对象2、如果需要转换的是List集合总结对象和集合分两种情况处理,目前我用的MP的版本

Python自动化处理PDF文档的操作完整指南

《Python自动化处理PDF文档的操作完整指南》在办公自动化中,PDF文档处理是一项常见需求,本文将介绍如何使用Python实现PDF文档的自动化处理,感兴趣的小伙伴可以跟随小编一起学习一下... 目录使用pymupdf读写PDF文件基本概念安装pymupdf提取文本内容提取图像添加水印使用pdfplum

C# LiteDB处理时间序列数据的高性能解决方案

《C#LiteDB处理时间序列数据的高性能解决方案》LiteDB作为.NET生态下的轻量级嵌入式NoSQL数据库,一直是时间序列处理的优选方案,本文将为大家大家简单介绍一下LiteDB处理时间序列数... 目录为什么选择LiteDB处理时间序列数据第一章:LiteDB时间序列数据模型设计1.1 核心设计原则

基于Redis自动过期的流处理暂停机制

《基于Redis自动过期的流处理暂停机制》基于Redis自动过期的流处理暂停机制是一种高效、可靠且易于实现的解决方案,防止延时过大的数据影响实时处理自动恢复处理,以避免积压的数据影响实时性,下面就来详... 目录核心思路代码实现1. 初始化Redis连接和键前缀2. 接收数据时检查暂停状态3. 检测到延时过

Java利用@SneakyThrows注解提升异常处理效率详解

《Java利用@SneakyThrows注解提升异常处理效率详解》这篇文章将深度剖析@SneakyThrows的原理,用法,适用场景以及隐藏的陷阱,看看它如何让Java异常处理效率飙升50%,感兴趣的... 目录前言一、检查型异常的“诅咒”:为什么Java开发者讨厌它1.1 检查型异常的痛点1.2 为什么说