给定一个长度为 nn 的整数数组 a1,a2,…,ana1,a2,…,an。
请你构造长度为 nn 的整数数组 b1,b2,…,bnb1,b2,…,bn,要求数组 bb 满足:
- b1=0b1=0。
- 对于任意一对索引 ii 和 jj(1≤i,j≤n1≤i,j≤n),如果 ai=ajai=aj 则 bi=bjbi=bj(注意,如果 ai≠ajai≠aj,则 bibi 和 bjbj 相等与否随意)。
- 对于任意索引 ii(i∈[1,n−1]i∈[1,n−1]),要么满足 bi=bi+1bi=bi+1,要么满足 bi+1=bi+1bi+1=bi+1。
请计算,一共可以构造出多少个不同的满足条件的数组 bb。
由于答案可能很大,你只需要输出对 998244353998244353 取模后的结果。
例如,如果 a=[1,2,1,2,3]a=[1,2,1,2,3],则一共有 22 个满足条件的数组 bb,分别是 b=[0,0,0,0,0]b=[0,0,0,0,0] 和 b=[0,0,0,0,1]b=[0,0,0,0,1]。
输入格式
第一行包含一个整数 nn。
第二行包含 nn 个整数 a1,a2,…,ana1,a2,…,an。
输出格式
一个整数,表示对 998244353998244353 取模后的结果。
数据范围
前 33 个测试点满足 2≤n≤52≤n≤5。
所有测试点满足 2≤n≤2×1052≤n≤2×105,1≤ai≤1091≤ai≤109。
输入样例1:
5
1 2 1 2 3
输出样例1:
2
#include<bits/stdc++.h>
using namespace std;
const int N=2e5+10,mod=998244353 ;
map<int,int>st,mp;//无序哈希这里会被卡
int a[N],b[N],c[N];
pair<int,int>p[N];
int main()
{
int n;
cin>>n;
for(int i=1;i<=n;i++)
{
cin>>a[i];
if(st[a[i]]==0)
{
st[a[i]]=i;//记录a[i]第一次出现的位置
}
mp[a[i]]=i;//记录a[i]最后一次出现的位置
}
long long res=0;
int i;
auto it=mp.begin(),t=st.begin();
for(i=1;it!=mp.end();it++,t++,i++)
{
int r=it->second,l=t->second;
p[i].first=l,p[i].second=r;
}
sort(p+1,p+i);//对区间进行排序,合并区间
int cnt=0,l=0,r=0;
for(int i=1;i<=n;i++)
{
if(p[i].first<r)
{
r=max(p[i].second,r);//如果左端点小于右端点,代表左端点在前一个区间的左右之间
//所以要更新下右端点的值
}
else
{
l=p[i].first;
r=p[i].second;
cnt++;//大于代表有一个新的区间,更新下左右区间
}
}
cnt--;
long long ans=1;
for(i=1;i<=cnt;i++){
ans=(ans*2)%mod;
}
printf("%d\n",ans);
}