题目链接

Problem Description

Chiaki has an array of n positive integers. You are told some facts about the array: for every two elements $$$a_i$$$ and  $$$a_j$$$ in the subarray $$$a_{l,r} (l ≤ i < j ≤ r )$$$, $$$a_i≠a_j$$$ holds.
Chiaki would like to find a lexicographically minimal array which meets the facts.

Input

There are multiple test cases. The first line of input contains an integer T, indicating the number of test cases. For each test case:
The first line contains two integers n,m (1 ≤ n,m  ≤ 10$$$^5$$$) -- the length of the array and the number of facts. Each of the next m lines contains two integers $$$ l_i$$$ and $$$r_i$$$ (1 ≤ $$$l_i$$$ ≤ $$$r_i$$$  ≤ 10$$$^5$$$)

It is guaranteed that neither the sum of all n nor the sum for all m exceeds 10$$$^6$$$.

 
Output

For each test case, output n integers denoting the lexicographically minimal array. Integers should be separated by a single space, and no extra spaces are allowed at the end of lines.

 
Sample Input

3
2 1
1 2
4 2
1 2
3 4
5 2
1 3
2 4

 
Sample Output

1 2

1 2 1 2

1 2 3 1 1

标程传送门

【题意】

给m个区间[$$$l_i, r_i$$$],要构造一个长度为n的串,每个区间内的数不能有相同的,且整个串的字典序最小

【思路】

要求字典序最小,自然想到要按从左到右的顺序对串进行填充,因为最左边的区间一定是从1开始填的,而它一旦填充,由于区间重叠,就会对后面的区间造成影响。在填充的过程中有两个问题需要解决:如何寻找下一个区间?如何维护下一个区间可以使用的数字?

首先可以肯定的是,如果一个区间被更大的区间包含,就再也不需要考虑它了,因为大的区间满足它也一定满足;因此,需要考虑的区间只可能两两重叠,或不重叠,所以它们的左右端点与其他区间都不一样。

假设现在处理到了位置$$$i$$$,有一个集合M,记录的是当前可用的所有数字,为了更快的生成M,不能每次都把所有数遍历一遍。从M中去掉位置$$$i$$$选择的数后,继续填充下一个位置$$$i+1$$$有两种可能:两点在同一个区间内,这样$$$i+1$$$直接从M中选一个最小的;两点在不同区间,这个时候[$$$l_{i+1},r_{i+1}$$$]可能已经填充了一部分了,也就是两区间的重叠部分[$$$l_{i+1},r_i$$$],M要加入一些数,变为[$$$l_i,l_{i+1}-1$$$]$$$\cup$$$ M,再取出最小的数填充到$$$i+1$$$。

因此,在填数的过程中需要不断获取区间的起点,对每个位置,都需要知道一个它所在的左端点。同一个位置可能会被多个区间覆盖,但由于实际填数的时候从左到右,所以只需要考虑最靠左的左端点。如果用预处理一遍用数组pre[]记录所有位置的这样的左端点,这些值的意义就是在处理位置$$$i$$$时,必须和位置pre[i]~$$$i-1$$$的数都不相同。

有了预处理以后,当前可用的数字集合M的维护过程就是,$$$M_{(i+1)} =  (M_{(i)}-{ans[i]})\cup\{ans[t]|t\in[pre[i], i-1]\}$$$。M上的操作:插入删除,求最小,所以可以用set来实现。

【代码】

#include<stdio.h>
#include<set>
using std::set;
using std::pair;
#define N_max 100005
typedef pair<int,int> PII;
typedef long long LL;
#define INF 0x3f3f3f3f
PII ipt[N_max];
int ans[N_max];int n, m;
int pre[N_max];
int main() {
int kase;
scanf("%d", &kase);
while (kase--)
{
scanf("%d %d", &n, &m);
int del = ; //所有右端点初始化为指向本身
for (int i = ; i <= n; i++)
{
pre[i] = i;
ans[i] = ;
} //输入并只记录最小的左端点
for (int i = ; i<m; ++i)
{
scanf("%d %d", &ipt[i].first, &ipt[i].second);
if (pre[ipt[i].second] > ipt[i].first)
pre[ipt[i].second] = ipt[i].first;
}
//更远的pre[i+1]会把pre[i]扩大到同样远
for (int i = n - ; i >= ; --i)
{
if (pre[i] >= pre[i + ])pre[i] = pre[i + ];
}
set<int>help;//最开始的时候把所有数都放进去
for (int i = ; i <= n + ; ++i)help.insert(i); for (int ri = ; ri <= n; ri++)//给所有位置选一个数
{
for (int t = pre[ri - ]; t<pre[ri]; ++t)//补充help
{
help.insert(ans[t]);
}
ans[ri] = *help.begin();//set的第一个数就是最小的
help.erase(help.begin());
}
for (int i = ; i <= n; ++i)printf("%d%c", ans[i], i == n ? '\n' : ' ');
} return ;
}

【总结】

看了很久标程,结合自己的理解写出来了。反思了一下之前自己的写法差不多,但是超时的原因,很有可能是在可用集合的维护上不够精简。如果每次直接填好一个区间→更新M→填下一个区间,其实很多数字在真正被使用前就已经被反复插入/删除了很多次,很浪费时间。

2018 杭电多校1 - Distinct Values的更多相关文章

  1. hdu6312 2018杭电多校第二场 1004 D Game 博弈

    Game Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total Submis ...

  2. 【2020杭电多校】Distinct Sub-palindromes 找规律

    题目链接:Distinct Sub-palindromes 题意: 给你一个长度n,你需要找出来一些串,这些串由A...Z和a...z构成.我们设长度为n的所有串中所包含回文子串最少的数量为ans.问 ...

  3. 2018 杭电多校3 - M.Walking Plan

    题目链接 Problem Description There are $$$n$$$ intersections in Bytetown, connected with $$$m$$$ one way ...

  4. 2018 杭电多校1 - Chiaki Sequence Revisited

    题目链接 Problem Description Chiaki is interested in an infinite sequence $$$a_1,a_2,a_3,...,$$$ which i ...

  5. 2018 杭电多校2 - Naive Operations

    题目链接 Problem Description In a galaxy far, far away, there are two integer sequence a and b of length ...

  6. 2018杭电多校第二场1003(DFS,欧拉回路)

    #include<bits/stdc++.h>using namespace std;int n,m;int x,y;int num,cnt;int degree[100007],vis[ ...

  7. 2018杭电多校第六场1009(DFS,思维)

    #include<bits/stdc++.h>using namespace std;int a[100010];char s[20];int zhiren[100010];vector& ...

  8. 2018杭电多校第五场1002(暴力DFS【数位】,剪枝)

    //never use translation#include<bits/stdc++.h>using namespace std;int k;char a[20];//储存每个数的数值i ...

  9. 2018杭电多校第三场1003(状态压缩DP)

    #include<bits/stdc++.h>using namespace std;const int mod =1e9+7;int dp[1<<10];int cnt[1& ...

随机推荐

  1. 【BZOJ4753】最佳团体(分数规划,动态规划)

    [BZOJ4753]最佳团体(分数规划,动态规划) 题面 BZOJ Description JSOI信息学代表队一共有N名候选人,这些候选人从1到N编号.方便起见,JYY的编号是0号.每个候选人都由一 ...

  2. LiteOS创建任务的一个BUG

    在任务创建的时候,参数无法传递,第二个参数本来是用来做参数传递的,但是却没用到,很尴尬啊,缺少了这个功能,很多无法写了? osThreadId_t osThreadNew (osThreadFunc_ ...

  3. Redis系列一 Redis安装

    Redis系列一    Redis安装 1.安装所使用的操作系统为Ubuntu16.04 Redis版本为3.2.9 软件一般下载存放目录为/opt,以下命令操作目录均为/opt root@ubunt ...

  4. php webservice 可能存在的坑

    场景: 今天在生产机器上调用webservice失败 报 ...failed to load external entity... wget一下地址发现报500错误  把wsdl去掉再wget 发现就 ...

  5. 从细节处谈Android冷启动优化

    本文来自网易云社区 Android APP冷启动优化,对于Android开发同学而言可能是个老生常谈的技优了. 之所以花时间写一篇冷启动优化的文章: 我想从另外一个角度来说冷启动优化,如题所述,从细节 ...

  6. python import vs from import

    https://stackoverflow.com/questions/9439480/from-import-vs-import

  7. Windows运行机理——主程序—WinMain

    Windows运行机理这系列文章都是来至于<零基础学Qt4编程>——吴迪,个人觉得写得很好,所以进行了搬运和个人加工 在windows 操作系统下,用C 或者C++来编写MS-DOS 应用 ...

  8. 记录---Testin上新手测试用例设计实战---碎乐3.2.0

    平台上给的版本是碎乐3.12版的,但是平台上给的安装包下载不了,所以加群咨询之后给出了直接去手机应用商店下载搜索到的版本的对策.所以就那应用商店中找到的3.2.0版本来设计测试用例.因为任务中没有给出 ...

  9. 推荐:一个适合于Python新手的入门练手项目

    随着人工智能的兴起,国内掀起了一股Python学习热潮,入门级编程语言,大多选择Python,有经验的程序员,也开始学习Python,正所谓是人生苦短,我用Python 有个Python入门练手项目, ...

  10. linux学习总结---mysql总结②

    函数: 字符串 日期时间 数学 子查询:嵌套查询 1. 做子查询: select sclass from studb where sname='..' 2.select * from studb wh ...