链接:https://ac.nowcoder.com/acm/contest/372/D
来源:牛客网
时间限制:C/C++ 1秒,其他语言2秒
空间限制:C/C++ 262144K,其他语言524288K
64bit IO Format: %lld
题目描述
可能很多人要吐槽为什么标题不是“救救blabla”了。
怪人PM6喜欢数糖纸,不同的糖纸有不同的颜色,一共有 N 张糖纸,第 i 张糖纸颜色为 Ci ,它们的位置都是固定的。PM6喜欢五彩缤纷的糖纸,所以他不希望有重复的颜色。他有一次机会,可以收集任意一段连续区间内的糖纸。求出PM6最多能收集多少张糖纸。
输入描述:
第一行一个正整数 N ,表示共有 N 张糖纸。 第二行共有 N 个正整数,第 i 个正整数表示第 i 张糖纸的颜色 Ci 对于20%的数据:1<=N<=100 对于40%的数据:1<=N<=1000 对于100%的数据:1<=N<=1e6,0<=Ci<=1e9
输出描述:
一个整数表示PM6最多能收集多少张糖纸。
示例1
输入
5 1 2 2 3 4
输出
3
说明
PM6可以收集第3到第5张的糖纸,共有三张。
分析:本题题意即为查找没有重复元素的最长区间段,我们可以利用桶排序的思想来判断区间段内是否有重复元素,来查找最长无重复元素区间段。不过数据范围是1e9,开普通数组可能会导致数组越界。我们就可以开一个比较另类的bool类型数组(长度居然可以达到1e11........),这样就可以存放数据了。
#include<stdio.h>
const int M=1e6+5,XM=1e9+5;
int a[M],n,i,j,k,l,r,Max,tMax;
bool b[XM];
int main()
{
scanf("%d",&n);//输入元素数量
for(i=1;i<=n;i++)//依次输入各个元素
{
scanf("%d",&a[i]);
}
l=1,r=1;
while(r<=n)//当末端进行区间段遍历,直到遍历到尾部(循环内最多遍历2e6次)
{
if(!b[a[r]])//如果该元素在区间段没有出现过
{
b[a[r]]=1;//对该元素进行标记
r++;//向后延伸
Max=(r-l)>Max?(r-l):Max;//判断该区间内是否为最大值
}
else//如果该元素在区间段内已经出现过了,这个元素之前的区间段即为最大值
{
while(b[a[r]])//将该区间段元素清零,为下一个区间段做准备
{
b[a[l]]=0;
l++;
}
}
}
printf("%d\n",Max);//输出最终的最大值
}