HDU6301

本文介绍了一道编程题的解决方案,题目要求根据给定的条件找到满足条件的最小字典序数组。通过使用set数据结构来跟踪不同区间内的元素,确保了每个子数组中元素的唯一性,并最终输出符合要求的数组。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

Distinct Values

Time Limit: 4000/2000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)
Total Submission(s): 3244    Accepted Submission(s): 1051


 

Problem Description

Chiaki has an array of n positive integers. You are told some facts about the array: for every two elements ai and aj in the subarray al..r (l≤i<j≤r ), ai≠aj 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 and m (1≤n,m≤105 ) -- the length of the array and the number of facts. Each of the next m lines contains two integers li and ri (1≤li≤ri≤n ).

It is guaranteed that neither the sum of all n nor the sum of all m exceeds 106 .

 

 

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

 

 

Source

2018 Multi-University Training Contest 1

用set来存每一次放进区间里面的元素,每个区间放完之后再把放回set里面为下一次使用。

不能清空数组,不然会超时?

#include<stack>
#include<queue>
#include<math.h>
#include<vector>
#include<string>
#include<stdio.h>
#include<map>
#include<set>
#include<iostream>
#include<string.h>
#include<algorithm>
#define maxn 100005
#define maxm 10000005
#define MAXN 100005
#define MAXM 10005
#define mem(a,b) memset(a,b,sizeof(a))
#define ll long long
#define inf 0x3f3f3f3f3f
using namespace std;
int a[maxn];
struct node{
    int l,r;
}d[2*maxn];
bool cmp(node n,node m){
    if(n.l==m.l)return n.r>m.r;
    return n.l<m.l;
}
int main(){
    int t;
    scanf("%d",&t);
    while(t--){
    set<int>s;
    set<int>::iterator it;
     int n,m;
     scanf("%d%d",&n,&m);
     for(int i=0;i<m;i++){
        scanf("%d%d",&d[i].l,&d[i].r);
     }
     sort(d,d+m,cmp);
     for(int i=1;i<=n;i++){
        a[i]=1;s.insert(i);
     }
     it=s.begin();
     int last=0,x=1;;
     for(int i=d[0].l;i<=d[0].r;i++){
        s.erase(x);a[i]=x++;
     }
     for(int i=1;i<m;i++){
        if(d[i].r<d[last].r)continue;
        for(int j=d[last].l;j<=min(d[last].r,d[i].l-1);j++){
            s.insert(a[j]);
        }
        for(int j=max(d[last].r+1,d[i].l);j<=d[i].r;j++){
            it=s.begin();
            a[j]=*it;s.erase(it);
        }
        last=i;
     }
     for(int i=1;i<=n;i++){if(i!=1)printf(" ");printf("%d",a[i]);}
     printf("\n");
    }
}

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值