Codeforces Round #312 (Div. 2) E. A Simple Task 线段树+计数排序
题目链接:
http://codeforces.com/problemset/problem/558/E
E. A Simple Task
time limit per test5 secondsmemory limit per test512 megabytes
#### 问题描述
> This task is very simple. Given a string S of length n and q queries each query is on the format i j k which means sort the substring consisting of the characters from i to j in non-decreasing order if k = 1 or in non-increasing order if k = 0.
>
> Output the final string after applying the queries.
输入
The first line will contain two integers n, q (1 ≤ n ≤ 105, 0 ≤ q ≤ 50 000), the length of the string and the number of queries respectively.
Next line contains a string S itself. It contains only lowercase English letters.
Next q lines will contain three integers each i, j, k (1 ≤ i ≤ j ≤ n, ).
输出
Output one line, the string S after applying the queries.
样例输入
10 5
abacdabcda
7 10 0
5 8 1
1 4 0
3 6 0
7 10 1
样例输出
cbcaaaabdd
题意
给你一个长度为n的字符串(只有小写字母),m个更新操作(l,r,type)要么对区间里面的字符串升序排,要么降序排,问m个更新之后最后的字符串是什么
题解
首先,只有26个字母,可以考虑计数排序,其次,当然是要用线段树来维护了,可以开26颗线段树,支持区间更新,区间查询。
对于更新区间先查询一下各个字母多少个,然后再按排完序的结果,26个字母(对应26颗线段树)全部干一发区间更新。
代码
#include<map>
#include<set>
#include<cmath>
#include<queue>
#include<stack>
#include<ctime>
#include<vector>
#include<cstdio>
#include<string>
#include<bitset>
#include<cstdlib>
#include<cstring>
#include<iostream>
#include<algorithm>
#include<functional>
using namespace std;
#define X first
#define Y second
#define mkp make_pair
#define lson (o<<1)
#define rson ((o<<1)|1)
#define mid (l+(r-l)/2)
#define sz() size()
#define pb(v) push_back(v)
#define all(o) (o).begin(),(o).end()
#define clr(a,v) memset(a,v,sizeof(a))
#define bug(a) cout<<#a<<" = "<<a<<endl
#define rep(i,a,b) for(int i=a;i<(b);i++)
#define scf scanf
#define prf printf
typedef __int64 LL;
typedef vector<int> VI;
typedef pair<int,int> PII;
typedef vector<pair<int,int> > VPII;
const int INF=0x3f3f3f3f;
const LL INFL=0x3f3f3f3f3f3f3f3fLL;
const double eps=1e-8;
const double PI = acos(-1.0);
//start----------------------------------------------------------------------
const int maxn=1e5+10;
int sumv[26][maxn<<2],setv[26][maxn<<2];
int n,m;
char str[maxn];
void maintain(int id,int o) {
sumv[id][o]=sumv[id][lson]+sumv[id][rson];
}
void pushdown(int id,int o,int l,int r) {
if(setv[id][o]<0) return;
sumv[id][lson]=(mid-l+1)*setv[id][o];
sumv[id][rson]=(r-mid)*setv[id][o];
setv[id][lson]=setv[id][rson]=setv[id][o];
setv[id][o]=-1;
}
void build(int id,int o,int l,int r) {
if(l==r) {
int idx=str[l]-'a';
if(id==idx) sumv[id][o]=1;
else sumv[id][o]=0;
} else {
build(id,lson,l,mid);
build(id,rson,mid+1,r);
maintain(id,o);
}
}
int ul,ur,uv;
void update(int id,int o,int l,int r) {
if(ul<=l&&r<=ur) {
sumv[id][o]=(r-l+1)*uv;
setv[id][o]=uv;
} else {
pushdown(id,o,l,r);
if(ul<=mid) update(id,lson,l,mid);
if(ur>mid) update(id,rson,mid+1,r);
maintain(id,o);
}
}
int ql,qr,qv;
void query(int id,int o,int l,int r) {
if(ql<=l&&r<=qr) {
qv+=sumv[id][o];
} else {
pushdown(id,o,l,r);
if(ql<=mid) query(id,lson,l,mid);
if(qr>mid) query(id,rson,mid+1,r);
maintain(id,o);
}
}
void init() {
clr(sumv,0);
clr(setv,-1);
}
int main() {
init();
scf("%d%d",&n,&m);
scf("%s",str+1);
rep(i,0,26) build(i,1,1,n);
rep(i,0,m) {
int l,r,type;
scf("%d%d%d",&l,&r,&type);
int lef=l;
if(type==1) {
rep(i,0,26) {
ql=l,qr=r,qv=0;
query(i,1,1,n);
ul=l,ur=r,uv=0;
update(i,1,1,n);
ul=lef,ur=lef+qv-1,uv=1;
if(ul<=ur) update(i,1,1,n);
lef+=qv;
}
} else {
for(int i=25; i>=0; i--) {
ql=l,qr=r,qv=0;
query(i,1,1,n);
ul=l,ur=r,uv=0;
update(i,1,1,n);
ul=lef,ur=lef+qv-1,uv=1;
if(ul<=ur){
// prf("(%d,%d),id:%d\n",ul,ur,i);
update(i,1,1,n);
}
lef+=qv;
}
}
}
for(int i=1;i<=n;i++){
rep(j,0,26){
ql=i,qr=i,qv=0;
query(j,1,1,n);
if(qv>0){
prf("%c",'a'+j);
break;
}
}
}
puts("");
return 0;
}
//end-----------------------------------------------------------------------
/*
10 1
abacdabcda
7 10 0
*/
Notes
以后需要建多颗线段树的时候最好把它们所有的操作都独立开,不要放在一起!因为放在一起反而有可能变麻烦。
Codeforces Round #312 (Div. 2) E. A Simple Task 线段树+计数排序的更多相关文章
- Codeforces Round #312 (Div. 2) E. A Simple Task 线段树
E. A Simple Task 题目连接: http://www.codeforces.com/contest/558/problem/E Description This task is very ...
- Codeforces Round #312 (Div. 2) E. A Simple Task 线段树 延时标记
E. A Simple Task time limit per test5 seconds memory limit per test512 megabytes inputstandard input ...
- Codeforces 588E. A Simple Task (线段树+计数排序思想)
题目链接:http://codeforces.com/contest/558/problem/E 题意:有一串字符串,有两个操作:1操作是将l到r的字符串升序排序,0操作是降序排序. 题解:建立26棵 ...
- Codeforces Round #312 (Div. 2) E. A Simple Task
题目大意就是给一个字符串,然后多个操作,每次操作可以把每一段区间的字符进行升序或者降序排序,问最终的字符串是多少. 一开始只考虑字符串中字符'a'的情况,假设操作区间[L,R]中有x个'a',那么一次 ...
- Codeforces Round #292 (Div. 1) C. Drazil and Park 线段树
C. Drazil and Park 题目连接: http://codeforces.com/contest/516/problem/C Description Drazil is a monkey. ...
- Codeforces Round #254 (Div. 1) C. DZY Loves Colors 线段树
题目链接: http://codeforces.com/problemset/problem/444/C J. DZY Loves Colors time limit per test:2 secon ...
- Codeforces Round #337 (Div. 2) D. Vika and Segments 线段树扫描线
D. Vika and Segments 题目连接: http://www.codeforces.com/contest/610/problem/D Description Vika has an i ...
- Codeforces Round #337 (Div. 2) D. Vika and Segments (线段树+扫描线+离散化)
题目链接:http://codeforces.com/contest/610/problem/D 就是给你宽度为1的n个线段,然你求总共有多少单位的长度. 相当于用线段树求面积并,只不过宽为1,注意y ...
- Codeforces Round #149 (Div. 2) E. XOR on Segment (线段树成段更新+二进制)
题目链接:http://codeforces.com/problemset/problem/242/E 给你n个数,m个操作,操作1是查询l到r之间的和,操作2是将l到r之间的每个数xor与x. 这题 ...
随机推荐
- emlog 百度熊掌号提交插件-基于Emlog6.0.1特别版美化
插件截图 插件简介 此插件在发布文章的时候自动向百度熊掌号提交,有利于百度熊掌号收录.基于Emlog6.0.1特别版美化的插件. 在百度推送插件的基础上修改制作而成与百度推送共存,解放双手,走向人生巅 ...
- Delphi获取Android下GPS的NMEA 0183数据
下面的程序,可以实现Android下获取GNSS的NMEA0183数据: unit utAndroidNmea; interface uses Androidapi.JNIBridge, Androi ...
- ACM1020:Encoding
Problem Description Given a string containing only 'A' - 'Z', we could encode it using the following ...
- js判断两个日期是否相等的方法
今天优化代码的时候,发现一个问题,js比较日期是否相等时,我用==去比较,发现两个时间不相等但是运行结果却是true,然后去百度了下发现oldStartTime, startTime都是对象,类型为引 ...
- 20155207JAVA第十二周课堂练习
20155207JAVA第十二周课堂练习 教材代码检查--P98 修改教材P98 Score2.java, 让执行结果数组填充是自己的学号 Arrays和String单元测试 在IDEA中以TDD的方 ...
- 20155211 2016-2017-2 《Java程序设计》第2周学习总结
20155211 2016-2017-2 <Java程序设计>第2周学习总结 教材学习内容总结 通过对教材的阅读,我理解到Java中对于整数,浮点数等类型的定义与c语言基本相同. 对字面常 ...
- 20155223 2006-2007-2 《Java程序设计》第二周学习总结
20155223 2006-2007-2 <Java程序设计>第二周学习总结 第三章内容总结 3.1 类型 正如我所预料的情况一样:Java脱胎于C语言,就一定会留有和C语言相近或相同的语 ...
- #333. 【NOIP2017】宝藏
#333. [NOIP2017]宝藏 http://uoj.ac/problem/333 1.错误的$n^42^n$做法: dp[s]表示当前的点集为s,然后从这些点中选一个做起点i,然后枚举边,然后 ...
- bzoj1011 遥远的行星
bzoj1011 遥远的行星 原题链接 题解 一道真正的玄学题.... 其实这题根本没法做 首先暴力这么跑:\[ans(s)=\sum_{i=1}^{\lfloor As\rfloor}\frac{M ...
- 监听Entity Framework生成的Sql语句
Entity Framework为我们提供了很大的方便,但有时候,我们想看看EF生成的Sql语句到底是怎样的,一种方式是我们可以启用Sql Server Profer工具.今天介 ...