2120: 数颜色

Time Limit: 6 Sec  Memory Limit: 259 MB
Submit: 3623  Solved: 1396
[Submit][Status][Discuss]

Description

墨墨购买了一套N支彩色画笔(其中有些颜色可能相同),摆成一排,你需要回答墨墨的提问。墨墨会像你发布如下指令: 1、 Q L R代表询问你从第L支画笔到第R支画笔中共有几种不同颜色的画笔。 2、 R P Col 把第P支画笔替换为颜色Col。为了满足墨墨的要求,你知道你需要干什么了吗?

Input

第1行两个整数N,M,分别代表初始画笔的数量以及墨墨会做的事情的个数。第2行N个整数,分别代表初始画笔排中第i支画笔的颜色。第3行到第2+M行,每行分别代表墨墨会做的一件事情,格式见题干部分。

Output

对于每一个Query的询问,你需要在对应的行中给出一个数字,代表第L支画笔到第R支画笔中共有几种不同颜色的画笔。

Sample Input

6 5
1 2 3 4 5 5
Q 1 4
Q 2 6
R 1 2
Q 1 4
Q 2 6

Sample Output

4
4
3
4

HINT

对于100%的数据,N≤10000,M≤10000,修改操作不多于1000次,所有的输入数据中出现的所有整数均大于等于1且不超过10^6。

2016.3.2新加数据两组by Nano_Ape

Source

 

[Submit][Status][Discuss]

这真是一道好题,貌似有好多种不同的做法。有人用树套树过的,有人用整体二分过的,有人用带修莫队过的,还有像我一样的蒟蒻用常数优化暴力过的。

虽然2016有新加数据,然而依然卡不住暴力,23333。

RunID User Problem Result Memory Time Language Code_Length Submit_Time
1734100 YOUSIKI 2120 Accepted 34496 kb 2340 ms C++/Edit 1411 B 2016-12-11 12:45:43
 #include <bits/stdc++.h>

 const int siz = ;

 char buf[siz], *bit = buf;

 inline int nextInt (void) {
register int ret = ;
register int neg = ; while (*bit < '')
if (*bit++ == '-')
neg ^= true; while (*bit >= '')
ret = ret* + *bit++ - ''; return neg ? -ret : ret;
} inline char nextChar (void) {
while (*bit != 'Q' && *bit != 'R')++bit;
return *bit ++;
} const int maxn = + ; int n, m;
int cases;
int total;
int answer;
int col[maxn];
int map[maxn];
int vis[maxn]; signed main (void) {
fread (buf, , siz, stdin); n = nextInt ();
m = nextInt (); for (register int i = ; i <= n; ++i) {
int color = nextInt ();
if (map[color] == )
map[color] = ++total;
col[i] = map[color];
} for (register int i = ; i <= n; ++i) {
switch (nextChar ()) {
case 'R' : {
int a = nextInt ();
int b = nextInt ();
if (map[b] == )
map[b] = ++total;
col[a] = map[b];
break;
}
case 'Q' : {
int a = nextInt ();
int b = nextInt ();
answer = , ++cases;
for (register int j = a; j <= b; ++j)
if (vis[col[j]] != cases)++answer, vis[col[j]] = cases;
printf("%d\n", answer);
}
}
}
}

然而不太理解为啥离散化一下就有这么大的用处。

RunID User Problem Result Memory Time Language Code_Length Submit_Time
1734122 YOUSIKI 2120 Time_Limit_Exceed 26684 kb 7632 ms C++/Edit 1289 B 2016-12-11 13:00:40
 #include <bits/stdc++.h>

 const int siz = ;

 char buf[siz], *bit = buf;

 inline int nextInt (void) {
register int ret = ;
register int neg = ; while (*bit < '')
if (*bit++ == '-')
neg ^= true; while (*bit >= '')
ret = ret* + *bit++ - ''; return neg ? -ret : ret;
} inline char nextChar (void) {
while (*bit != 'Q' && *bit != 'R')++bit;
return *bit ++;
} const int maxn = + ; int n, m;
int cases;
int answer;
int col[maxn];
int vis[maxn]; signed main (void) {
fread (buf, , siz, stdin); n = nextInt ();
m = nextInt (); for (register int i = ; i <= n; ++i)
col[i] = nextInt (); for (register int i = ; i <= m; ++i) {
switch (nextChar ()) {
case 'R' : {
int a = nextInt ();
int b = nextInt ();
col[a] = b;
break;
}
case 'Q' : {
int a = nextInt ();
int b = nextInt ();
answer = , ++cases;
for (register int j = a; j <= b; ++j)
if (vis[col[j]] != cases)++answer, vis[col[j]] = cases;
printf ("%d\n", answer);
}
}
}
}

当然,小生来写这道题不是为了练习暴力的,是为了学习带修莫队的。

有别于普通的莫队,带修莫队多了一维对时间的要求,每个询问可以表示为[l,r,t],表示区间需要我们维护到区间[l,r]在时刻t的存在情况。方法是,对于l,r还按照普通莫队的对l分组方式分组,组内对r排序,转移的时候暴力调整时间即可。貌似为了达到最优秀的复杂度,分组时的大小需要调整一下,但这题显然没有那么苛刻啦,o(* ̄▽ ̄*)ブ

 #include <bits/stdc++.h>

 const int siz = ;

 char buf[siz], *bit = buf;

 inline int nextInt (void) {
register int ret = ;
register int neg = ; while (*bit < '')
if (*bit++ == '-')
neg ^= true; while (*bit >= '')
ret = ret* + *bit++ - ''; return neg ? -ret : ret;
} inline char nextChar (void) {
while (*bit != 'Q' && *bit != 'R')++bit;
return *bit ++;
} const int maxn = + ;
const int maxm = + ; int n, m;
int l, r;
int s, t;
int answer;
int col[maxn];
int vis[maxm]; struct query {
int l, r, id, ans;
}qry[maxn]; int q; struct change {
int p, a, b, id;
}chg[maxn]; int c; inline bool cmp_lr (const query &A, const query &B) {
if (A.l / s != B.l / s)
return A.l < B.l;
else
return A.r < B.r;
} inline bool cmp_id (const query &A, const query &B) {
return A.id < B.id;
} inline void removeColor (int c) {
if (--vis[c] == )--answer;
} inline void insertColor (int c) {
if (++vis[c] == )++answer;
} inline void removeChange (change &c) {
col[c.p] = c.a;
if (c.p >= l && c.p <= r) {
removeColor(c.b);
insertColor(c.a);
}
} inline void insertChange (change &c) {
col[c.p] = c.b;
if (c.p >= l && c.p <= r) {
removeColor(c.a);
insertColor(c.b);
}
} inline void solve (query &q) {
while (t > && chg[t].id > q.id)
removeChange (chg[t--]);
while (t < c && chg[t + ].id < q.id)
insertChange (chg[++t]); while (l < q.l)removeColor (col[l++]);
while (l > q.l)insertColor (col[--l]);
while (r < q.r)insertColor (col[++r]);
while (r > q.r)removeColor (col[r--]); q.ans = answer;
} signed main (void) {
fread (buf, , siz, stdin); n = nextInt ();
m = nextInt (); for (register int i = ; i <= n; ++i)
col[i] = nextInt (); for (register int i = ; i <= m; ++i) {
switch (nextChar ()) {
case 'R' : {
chg[++c].id = i;
chg[c].p = nextInt ();
chg[c].b = nextInt ();
chg[c].a = col[chg[c].p];
col[chg[c].p] = chg[c].b;
break;
}
case 'Q' : {
qry[++q].id = i;
qry[q].l = nextInt ();
qry[q].r = nextInt ();
}
}
} s = sqrt (n); t = c; answer = ; l = ; r = ; std::sort (qry + , qry + + q, cmp_lr); for (register int i = ; i <= q; ++i)solve(qry[i]); std::sort (qry + , qry + + q, cmp_id); for (register int i = ; i <= q; ++i)
printf ("%d\n", qry[i].ans);
}

@Author: YouSiki

BZOJ 2120: 数颜色的更多相关文章

  1. BZOJ 2120 数颜色(带修改的莫队)

    2120: 数颜色 Time Limit: 6 Sec  Memory Limit: 259 MB Submit: 3478  Solved: 1342 [Submit][Status][Discus ...

  2. BZOJ 2120: 数颜色 分块

    2120: 数颜色 Time Limit: 20 Sec Memory Limit: 256 MB 题目连接 http://www.lydsy.com/JudgeOnline/problem.php? ...

  3. Bzoj 2120: 数颜色 && 2453: 维护队列 莫队,分块,bitset

    2120: 数颜色 Time Limit: 6 Sec  Memory Limit: 259 MBSubmit: 2645  Solved: 1039[Submit][Status][Discuss] ...

  4. BZOJ 2120 数颜色 (带修莫队)

    2120: 数颜色 Time Limit: 6 Sec  Memory Limit: 259 MBSubmit: 6367  Solved: 2537[Submit][Status][Discuss] ...

  5. BZOJ 2120 数颜色 【带修改莫队】

    任意门:https://www.lydsy.com/JudgeOnline/problem.php?id=2120 2120: 数颜色 Time Limit: 6 Sec  Memory Limit: ...

  6. bzoj 2120 数颜色 题解

    转载请注明:http://blog.csdn.net/jiangshibiao/article/details/23990489 [原题] 2120: 数颜色 Time Limit: 6 Sec  M ...

  7. bzoj 2120 数颜色 (带修莫队)

    题目链接: https://www.lydsy.com/JudgeOnline/problem.php?id=2120 题意:两种操作:Q 询问区间  l - r  内颜色的种类 ,R 单点修改 思路 ...

  8. BZOJ 2120 数颜色(带修改莫队)

    [题目链接] http://www.lydsy.com/JudgeOnline/problem.php?id=2120 [题目大意] 给出一颜色序列,每次可以修改一个位置的颜色或者询问一个区间不同颜色 ...

  9. BZOJ 2120 数颜色&2453 维护队列 [带修改的莫队算法]【学习笔记】

    2120: 数颜色 Time Limit: 6 Sec  Memory Limit: 259 MBSubmit: 3665  Solved: 1422[Submit][Status][Discuss] ...

随机推荐

  1. 遇到别人留下的storyboard的,你需要一个引导图,但是不知道怎么跳转.

    首先在AppDeledate.m文件里是这样. { self.window = [[UIWindow alloc]initWithFrame:[UIScreen mainScreen].bounds] ...

  2. iOS开发之功能模块--高仿Boss直聘的常用语的开发

    首先上Boss直聘的功能界面截图,至于交互请读者现在Boss直聘去交互体验:     本人的公司项目要高仿Boss直聘的IM常用语的交互功能,居然花费了我前后17个小时完成,这回自己测试了很多遍,代码 ...

  3. JS实现HTML标签转义及反转义

    今天我用ueditor时候遇到一个问题: 我从数据库中读取内容进行编辑的时候,不是有一些html标签嘛,从数据库读出来没有问题: 但是我用asp.net mvc,把读取出来的内容通过ueditor的a ...

  4. php CGI、Fastcgi、PHP-FPM的详细介绍与之间的关系

    以下PHP CGI.Fastcgi.PHP-FPM的一些信息归纳和汇总----->详细介绍与之间的关系 一:CGI是干嘛的?CGI是为了保证web server传递过来的数据是标准格式的 web ...

  5. Linux下安装Nginx1.9.3

    操作系统:CentOS6.5 64bit Nginx: 1.9.3 1.下载Nginx [root@iZ94jj63a3sZ softs]# wget http://nginx.org/downloa ...

  6. Ubuntu开发笔记

    这些操作在ubuntu14.04.1或者ubuntu12.04.5中进行 首先,安装ubuntu12.04(LTS)版本 安装按照高级安装方式,系统分配40G如下: /dev/sda*   ext4 ...

  7. 安卓直播开源: RTMP 推流SDK

    前些日子在github上提交了基于GPUImage的IOS直播推流SDK(https://github.com/runner365/GPUImageRtmpPush) 最近整理了android直播推流 ...

  8. 找不到mysql.sock,mysql.sock丢失问题解决方法

    Can 't connect to local MySQL server through socket '/var/lib/mysql/mysql.sock '(2) "; 是你的mysql ...

  9. 【WPF高级】Cue or Hint or Watermark or Placehoder in Controls(为控件添加提示,水印,占位符)

      通过Style实现对Texbox添加水印 <Style x:Key="placeHolder" TargetType="{x:Type TextBox}&quo ...

  10. java设计模式之观察者模式

    观察者模式 观察者模式(有时又被称为发布(publish )-订阅(Subscribe)模式.模型-视图(View)模式.源-收听者(Listener)模式或从属者模式)是软件设计模式的一种.在此种模 ...