复杂度没有问题,纯纯常数大,孩子卡了一晚上了,求求救救我吧。
#include<bits/stdc++.h>
#pragma GCC optimize(3)
#pragma GCC target("avx,avx2,sse,sse2")
#define pb push_back
#define il inline
using namespace std;
const int N = 1e6 + 10;
using ll = long long;
int n, stk[N], top, L[N], R[N], c[N];
struct Node{ int mx, cnt, tag; }t[N << 2];
#define ls (p << 1)
#define rs (p << 1 | 1)
#define lc ls, l, mid
#define rc rs, mid + 1, r
#define mid (l + r >> 1)
il void upd(int p, int z) { t[p].mx += z; t[p].tag += z; }
il void down(int p) {
upd(ls, t[p].tag);
upd(rs, t[p].tag);
t[p].tag = 0;
}
il void up(int p) {
t[p].mx = max(t[ls].mx, t[rs].mx);
t[p].cnt = (t[ls].mx == t[p].mx) ? t[ls].cnt : 0;
t[p].cnt += (t[rs].mx == t[p].mx) ? t[rs].cnt : 0;
}
il void bld(int p = 1, int l = 1, int r = n) {
t[p] = {0, r - l + 1, 0};
if(l == r) return;
bld(lc); bld(rc); up(p);
}
il void mdf(int x, int y, int z, int p = 1, int l = 1, int r = n) {
if(x <= l && r <= y) return upd(p, z);
down(p);
if(x <= mid) mdf(x, y, z, lc);
if(mid < y) mdf(x, y, z, rc);
up(p);
}
vector<array<int, 4>> vec[60];
ll ans, a[N];
il void init() {
for(int i = 1; i <= n; i++) {
while(top && a[stk[top]] < a[i]) R[stk[top]] = i - 1, top--;
L[i] = stk[top] + 1;
stk[++top] = i;
}
while(top) R[stk[top--]] = n;
for(int i = 1; i <= n; i++) {
vec[c[i]].push_back({L[i], i, R[i], 1});
vec[c[i]].push_back({i + 1, i, R[i], -1});
}
}
il char gc() {
static char buf[1000000], *p1 = buf, *p2 = buf;
return p1 == p2 && (p2 = (p1 = buf) + fread(buf, 1, 1000000, stdin), p1 == p2) ? EOF : *p1++;
}
il ll read() {
ll x = 0; char c = gc();
while(!isdigit(c)) c = gc();
while(isdigit(c)) x = (x << 1) + (x << 3) + (c ^ 48), c = gc();
return x;
}
signed main() {
n = read();
for(int i = 1; i <= n; i++) a[i] = read(), c[i] = __builtin_popcountll(a[i]);
init(); for(int i = 1; i <= n; i++) a[i] = -a[i]; init();
for(int b = 0; b <= 59; b++) {
if(vec[b].empty()) continue;
bld(); sort(begin(vec[b]), end(vec[b]));
for(int i = 1, j = 0; i <= n; i++) {
while(j < vec[b].size() && vec[b][j][0] <= i)
mdf(vec[b][j][1], vec[b][j][2], vec[b][j][3]), j++;
ans += t[1].mx == 2 ? t[1].cnt : 0;
}
}
printf("%lld", ans);
return 0;
}