记一个问题的AC
今天突然做一道LCT的染色问题的时候突然想到一个两个月前一道没有AC的题目。
大意是,给一个长度为10^4的序列,最多有255个不同的数字,有最多10^5次方个询问,对于每个询问 l,r 输出[l,r]中不同数字的数目。
记得最初的想法是 用f[i][j],存下数字i的第j次出现位置的下标 ,对每次询问,二分查找,判断每个数字i是否存在在[l,r]内的下标。
时间复杂度是最多是 O((10^5)*255*log(10^4)) ,结果比赛的时候超时了,加了读入优化还是不行。
由于比赛的OJ运行偏慢,1s的时限 比赛结束,只有3个人AC,最快的400ms,有一个刚刚好1000ms。
于是我发了个帖子,询问答案,果然得到了更好的思路:
1.
离散化,C[i][j]::A[1]..A[i]中值为j的数的个数
则数k在[L..R]中出现 <=> C[i][R]-C[i][L-1]>0.
一次询问时间(255),时间复杂度是O(10^5*255)
已经优化了一点点
代码:
#include <cstdio>
#include <cstdlib>
#include <time.h>
#include <iostream>
using namespace std;
const int INF = ; int f[INF][],pos[INF];
int g[INF];
int n, m, tol;
inline void rd (int &xx) {
char ch = getchar();
while (ch < '' || ch > '') ch = getchar();
for (xx = ; ch >= '' && ch <= ''; ch = getchar() )
xx = xx * + (ch - '');
}
char o[];
inline void putnum (int x) {
if (x == ) {putchar (''); return;}
int i;
for (i = ; x != ; i++, x /= ) o[i] = x % + '' ;
for (i--; i >= ; i--) putchar (o[i]);
putchar ();
}
int main() {
rd (n); rd (m);
for (int i = ; i <= n; i++) {
rd (g[i]);
if (!pos[g[i]]) pos[g[i]] = ++tol;
}
for (int i = ; i <= n; i++) {
for (int j = ; j <= tol; j++)
f[i][j] = f[i - ][j] + (pos[g[i]] == j);
}
for (int i = , l, r; i <= m; i++) {
int ans = ;
rd (l), rd (r);
for (int j = ; j <= tol; j++)
if (f[r][j] - f[l - ][j]) ans++;
putnum (ans);
}
return ;
}
可是在加上了读入和输出优化和依旧超时!
2.
把所有询问存下来,并按照l由小到大的顺序依次回答。当左端点为t时,考虑一个数组b[],若b[i]=1则表示a[i]在a[t]到a[i-1]都没出现过,否则b[i]=0。
那么任意一个左端点l=t,右端点r的询问都可以查询b[1]到b[r]的和得到答案。这个求区间和的操作可以用树状数组或线段树来解决。
当回答完l=t的询问,要回答l=t+1的询问时,涉及到b[]数组的修改。发现只需要把b[t]由1变0,把b[right[t]]由0变1,其中a[t]右边第一个和它相等的数是a[right[t]],可以预处理出来。这两个修改对于树状数组来说太容易了,然后本题就做完了。
补一句,如果题目要求强制在线,就把树状数组换成可持久化线段树,就搞定了。
时间复杂度可以优化至 O(NlogN+Q)
思路真是太棒了!看完这个我感觉这就是我想要的。
于是再经过无数TLE,优化,TLE,再优化终于AC了,并且只用了234ms!
#include <cstdio>
#include <cstdlib>
#include <time.h>
#include <iostream>
using namespace std; const int INF = ; int b[INF], ans[INF], qhead[INF], qr[INF], skip[INF];
int g[INF], ne[INF], last[INF];
int n, m, tol;
inline void rd (int &xx) {
char ch = getchar();
while (ch < '' || ch > '') ch = getchar();
for (xx = ; ch >= '' && ch <= ''; ch = getchar() )
xx = xx * + (ch - '');
}
char o[];
inline void putnum (int x) {
if (x == ) {putchar (''); return;}
int i;
for (i = ; x != ; i++, x /= ) o[i] = x % + '' ;
for (i--; i >= ; i--) putchar (o[i]);
putchar ();
}
int main() {
rd (n); rd (m);
for (int i = ; i <= n; i++) rd (g[i]);
for (int i = , x; i <= m; i++) {
rd (x), rd (qr[i]);
skip[i] = qhead[x];
qhead[x] = i;
}
for (int i = ; i <= n; i++) {
int t = g[i];
if (last[t] == ) for (int x = i; x <= n; x += x & -x) ++b[x];
ne[last[t]] = i, last[t] = i;
}
for (int i = ; i <= n; i++) {
if (qhead[i])
for (int t = qhead[i]; t; t = skip[t])
for (int x = qr[t]; x > ; x -= x & -x) ans[t] += b[x]; for (int x = i; x <= n; x += x & -x) --b[x];
if (ne[i] != ) for (int x = ne[i]; x <= n; x += x & -x) ++b[x];
}
for (int i = ; i <= m; i++)
putnum (ans[i]); }
感谢回答我问题的 nodgd 和 Hoblovski
记一个问题的AC的更多相关文章
- 记一个社交APP的开发过程——基础架构选型(转自一位大哥)
记一个社交APP的开发过程——基础架构选型 目录[-] 基本产品形态 技术选型 最近两周在忙于开发一个社交App,因为之前做过一点儿社交方面的东西,就被拉去做API后端了,一个人头一次完整的去搭这么一 ...
- 记一个常见的ms sql server中取第N条记录的方法
前言 好好学习,天天向上. 正文 好像也是一个不难的问题,刚视频里看到的,就记一下吧. 下面是表中原始的数据结构,做了一个倒叙排序: select * from Employee order by S ...
- 记一个mvn奇怪错误: Archive for required library: 'D:/mvn/repos/junit/junit/3.8.1/junit-3.8.1.jar' in project 'xxx' cannot be read or is not a valid ZIP file
我的maven 项目有一个红色感叹号, 而且Problems 存在 errors : Description Resource Path Location Type Archive for requi ...
- 记一个简单的sql查询
在我们做各类统计和各类报表的时候,会有各种各样的查询要求.条件 这篇主要记录一个常见的统计查询 要求如下: 统计一段时间内,每天注册人数,如果某天没有人注册则显示为0 现在建个简单的表来试试 建表语句 ...
- Entity Framework学习笔记——记一个错误解决方式及思路
继续之前设定的学习目标前,先来一篇小小的外篇.按照第一篇里的配置方式配置好的工程前两天还能正常工作,昨天却突然无法通过Add-Migration命令进行数据库的升级.错误信息如下: System.Da ...
- 记一个界面刷新相关的Bug
今天遇到一个比较有意思的bug, 这里简单记录下. Bug的症状是通过拖拉边框把我们客户端主窗口拖小之后,再最大化,会发现窗口显示有问题, 看起来像是刷新问题, 有些地方显示的不对了. 这里要说明的是 ...
- 记一个同时支持模糊匹配和静态推导的Atom语法补全插件的开发过程: 序
简介 过去的一周,都睡的很晚,终于做出了Atom上的APICloud语法提示与补全插件:apicloud_autocomplete.个中滋味,感觉还是有必要记录下来的.代码基于 GPL-3.0 开源, ...
- 记一个eclipse 错误 Undefined variable from import: randrange
我自己定义了一个random.py 和pev的包含路径一样的 解决办法是: 出现这种问题,可以import 这个模块,print 这个模块
- 记一个dynamic的坑
创建一个控制台程序和一个类库, 在控制台创建一个匿名对象,然后再在类库中访问它,代码如下: namespace ConsoleApplication1 { class Program { static ...
随机推荐
- Google Map API 代码示例
- ASP.Net 验证视图状态 MAC 失败
错误信息: 验证视图状态 MAC 失败.如果此应用程序由网络场或群集承载,请确保 <machineKey> 配置指定了相同的 validationKey 和验证算法.不能在群集中使用 Au ...
- Centos6快速yum lamp
yum install httpd httpd-devel mysql mysql-server mysql-devel php php-mysql php-common php-gd php-mb ...
- 转 :hdoj 4857 逃生【反向拓扑】
逃生 Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)Total Submissi ...
- java中main函数解析(转载)
从写java至今,写的最多的可能就是主函数 public static void main(String[] args) {} 但是以前一直都没有问自己,为什么要这么写,因为在c语言中就没有这样子的要 ...
- ASP.NET常用导出Excel方法汇总
本文转载:http://mattberseth.com/blog/2007/04/export_gridview_to_excel_1.html http://geekswithblogs.net/a ...
- SVN太旧,要更新问题
同步或者提交的时候出现问题提示 The working copy needs to be upgradedsvn: Working copy 'E:\JAVA\Workspaces\uhr' is t ...
- C程序中唯一序列号的生成
在实际的软件开发项目中.常常会涉及唯一序列号的生成.本文以一个实际的程序为例,介绍了唯一序列号的生成过程. 本文生成的序列号的样式为:MMDDHHMINSS_XXXXXX. 程序例如以下: /**** ...
- android 01
安卓开源(就是免费),谷歌收购后推出,可以山寨(小米,三星都是安卓的山寨),ios不是开源(苹果应用要商用就要交钱).安卓3.0是平板,现在安卓至少是4.0以上,否则out了. 微软主要是系统和off ...
- CFS: 虚拟运行时间
http://edsionte.com/techblog/archives/4331 nice和prio的关系如下: #define NICE_TO_PRIO(nice) (MAX_RT_PRIO+n ...