分析:水题。枚举一个左区间,然后二分一个满足的右区间。算贡献即可。
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
int a[200010];
int maxl[200010*2][30];
int minl[200010*2][30];
int n,kk;
void S_table()
{
int l = int(log((double)n)/log(2.0));
for (int j=1;j<=l;j++)
{
for (int i=1; i + (1 << (j-1) ) - 1 <=n;++i)
{
maxl[i][j] = max(maxl[i][j-1], maxl[i + (1 << (j-1) )][j-1]);
minl[i][j] = min(minl[i][j-1], minl[i + (1 << (j-1) )][j-1]);
}
}
}
int rmq(int l, int r)
{
int k = int(log((double)(r-l+1))/log(2.0));
int a1 = max(maxl[l][k], maxl[r - (1<<k) + 1][k]);
int a2 = min(minl[l][k], minl[r - (1<<k) + 1][k]);
return a1-a2<=kk;
}
int main()
{
scanf("%d%d",&n,&kk);
for(int i=1;i<=n;++i)
{
scanf("%d",&a[i]);
maxl[i][0]=minl[i][0]=a[i];
}
S_table();
ll ans=n;
for(int i=1;i<n;i++)
{
int l=i,r=n;int pos=i;
while(r>=l)
{
int mid=(l+r)>>1;
if(rmq(i,mid))pos=mid,l=mid+1;
else r=mid-1;
}
ans+=pos-i;
}
printf("%lld\n",ans);
return 0;
}