iTranslated by AI
Competitive Programming Tutorial: ABC098D
Introduction
This article aims to improve both the author's and readers' algorithmic skills by carefully explaining some of the problems encountered during daily training.
Problem
Discussion
The following theorem holds:
For any non-negative integers
and a , b holds. Equality holds if and only if a \oplus b \le a + b . a \land b = 0
From this theorem, when
Therefore, the brute-force solution to this problem is as follows:
let mut counter = 0
for l in 0..n {
let mut r = l + 1;
let mut acc_sum = a[l];
while r < n && acc_sum & a[r] == 0 {
acc_sum += a[r];
r += 1
}
counter += r - l
}
The code above will result in TLE as is, but with a slight improvement, the time complexity can be reduced to
When while loop terminates in at most
Solution Example
use itertools::Itertools;
use proconio::input;
fn main() {
input! { n: usize, mut a: [u32; n], }
let next_nonzero = {
let mut res = (0..n)
.rev()
.scan(n, |state, i| {
let res = Some(*state);
if a[i] > 0 {
*state = i
}
res
})
.collect_vec();
res.reverse();
res
};
let mut res = 0;
for l in 0..n {
let mut r = next_nonzero[l];
let mut acc_sum = a[l];
// up to 20 steps
while r < n && acc_sum & a[r] == 0 {
acc_sum += a[r];
r = next_nonzero[r]
}
res += r - l
}
println!("{}", res)
}
Discussion