Problem F
题意:给出长度为n的序列a,问有多少个区间[L,R]满足 a[L]|a[L+1]|...a[R] >max(a[L],...a[R]).
n<=2e5, 0<=a[i]<=1e9.
先用单调栈O(n)求出a[i]最为最大值的区间[L,R].
找到a[i]最左边(右边)a[j] 满足 a[i]|a[i-1]|..a[j] >a[i] 即a[j]二进制中存在a[i]没有的bit.[x,y].
即a[i]|a[i-1]..|a[x-1]时的值是不变的.
题意:给出长度为n的序列a,问有多少个区间[L,R]满足 a[L]|a[L+1]|...a[R] >max(a[L],...a[R]).
n<=2e5, 0<=a[i]<=1e9.
先用单调栈O(n)求出a[i]最为最大值的区间[L,R].
找到a[i]最左边(右边)a[j] 满足 a[i]|a[i-1]|..a[j] >a[i] 即a[j]二进制中存在a[i]没有的bit.[x,y].
即a[i]|a[i-1]..|a[x-1]时的值是不变的.
容易算出以a[i]为最大值时,a[L]|a[L+1]|...a[R] < max(a[L],...a[R])区间个数.左端点有i-x+1种选法 右端点有b-y+1种.
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
const int N=2e5+20;
int n,a[N],L[N],R[N];
int le[32][N],rg[32][N];
stack<int> s;
int main()
{
scanf("%d",&n);
for(int i=0;i<n;i++)
scanf("%d",&a[i]);
for(int i=0;i<n;i++)
{
while(!s.empty()&&a[s.top()]<a[i])
R[s.top()]=i-1,s.pop();
L[i]=s.empty()?0:s.top()+1;
R[i]=n-1;
s.push(i);
}
for(int j=0;j<30;j++)
{
for(int i=0;i<n;i++)
{
int h=i;
while(h<n&&((a[i]>>j)&1)==((a[h]>>j)&1))
h++;
h--;
for(int k=i;k<=h;k++)
le[j][k]=i,rg[j][k]=h;
i=h;
}
}
ll res=0;
for(int i=0;i<n;i++)
{
int l=L[i],r=R[i];
for(int j=0;j<30;j++)
{
if((a[i]>>j)&1)
continue;
l=max(l,le[j][i]);
r=min(r,rg[j][i]);
}
res+=(i-l+1ll)*(r-i+1ll);
}
ll ans=1ll*n*(n+1)/2 - res;
cout<<ans<<endl;
return 0;
}