Disclaimer: If you want to reprint, can be explained in the comments directly, thank you! https://blog.csdn.net/SSL_ZYC/article/details/91045660
Subject to the effect:
Topic links: https://jzoj.net/senior/#main/show/4804
Ideas:
Obviously, for the arbitrary determination
, to meet the requirements of the subject is certainly left sequence is a contiguous segment
.
And this range is clearly monotone nature.
So you can use three pointers maintenance
. Every time the
pointer right one when maintenance
and
, then the answer to accumulate it.
Amortized time complexity is
Code:
**#include <cstdio>
#include <algorithm>
using namespace std;
typedef long long ll;
const int N=200010;
int n,m,l1,l2,r,sum,a[N],L[N],R[N],cnt1[N],cnt2[N];
ll ans;
int main()
{
freopen("survey.in","r",stdin);
freopen("survey.out","w",stdout);
scanf("%d%d",&n,&m);
for (int i=1;i<=n;i++)
scanf("%d",&a[i]);
for (int i=1;i<=m;i++)
{
scanf("%d%d",&L[i],&R[i]);
if (!L[i]) sum++;
}
l1=l2=1;
for (r=1;r<=n;r++)
{
cnt1[a[r]]++;
cnt2[a[r]]++;
if (cnt2[a[r]]==L[a[r]]) sum++;
while (cnt1[a[r]]>R[a[r]])
{
cnt1[a[l1]]--;
l1++;
}
while (sum==m&&l2<=r)
{
cnt2[a[l2]]--;
if (cnt2[a[l2]]==L[a[l2]]-1) sum--;
l2++;
}
ans+=max((ll)l2-(ll)l1,0LL);
}
printf("%lld\n",ans);
return 0;
}