Codeforces Round #512 E - Vasya and Good Sequences

Posted mltang

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Codeforces Round #512 E - Vasya and Good Sequences相关的知识,希望对你有一定的参考价值。

有时候觉得自己就是个思路搬运机,只会搬运思路

 

这个题首先说了求的是好区间的个数,  好区间满足条件: 1、二进制位1的数量和为偶数    2、w[i]表示a[i]的二进制上1的个数 ,sum[i] = w[1] + ... + w[i],对于l-r区间上任意一个位置j,w[j] < sum[r] - sum[l] - w[j]

 

设置一个dp[n][2] 数组,dp[i][0]代表     以i为结尾的,区间内二进制1的个数和为偶数的    区间个数

          dp[i][1]代表     以i为结尾的,区间内二进制1的个数和为奇数的    区间个数

 

然后再用dp[i][0]  -  所有不满足条件2的区间,把所有满足的区间求和即可

 

这个1<=a[i] <= 1e8  1e8比这个long long要小,60二进制位就可以保存,    所以这个  l - r  这个区间    最大的w[j] 其实也就是60不到,最小的w[i] 也是1 ,所以当你这个区间长度大于60,必定满足条件2

 

附上我丑陋无比的ac代码

 #include<iostream>
#include<queue>
#include<cstring>
#include<vector>
#include<cstdio>
#include<cmath>
#include<map>
#include<string>
using namespace std;
#define ll long long
#define se second
#define fi first
int n;
const int maxn = 300010;
long long arr[maxn];
int w[maxn];
int sum[maxn];
int dp[maxn][2];
int main()
{
    memset(w,0,sizeof(w));
    scanf("%d",&n);
    for(int i = 1 ; i <= n; ++i)
    {
        scanf("%lld",arr+i);
        long long k = 1;
        for(int j = 0; j < 62; ++j, k <<= 1)
        {
            if( k & arr[i] )
                w[i] ++;
        }
        //cout << w[i] << endl;
    }
    dp[1][0] = dp[1][1] = dp[0][0] = dp[0][1] = 0;
    for(int i = 2; i <= n; ++i)
    {
        //cout << w[i] << endl;
        if(w[i] % 2 == 1)
        {
            dp[i][0] = dp[i-1][1]+(w[i-1]%2);
            dp[i][1] = dp[i-1][0]+!(w[i-1]%2);
        }
        else
        {
            dp[i][0] = dp[i-1][0]+!(w[i-1]%2);
            dp[i][1] = dp[i-1][1]+(w[i-1]%2);
        }
    }
    ll ans = 0;
    for(int i = 2; i <= n; ++i)
    {
        ll add = 0;
        ll mx = w[i];
        ll sum = w[i];
        for(int j = i-1; j >= 1 && i-j<=70; --j)
        {
            if(mx < w[j]) mx = w[j];
            sum += w[j];
            if(mx > sum - mx && sum % 2 == 0)
                add --;
        }
        //cout << dp[i][0] << endl;
        //cout << add << endl;
        add += dp[i][0];
        ans += add;
    }
    printf("%lld
",ans);
}

 

以上是关于Codeforces Round #512 E - Vasya and Good Sequences的主要内容,如果未能解决你的问题,请参考以下文章

codeforces round 512 F. Putting Boxes Together 树状数组维护区间加权平均数

Codeforces Round #512 (Div. 2, based on Technocup 2019 Elimination Round 1) C. Vasya and Golden Tick

Codeforces Round #512 (Div. 2) D. Vasya and Triangle

Codeforces Round #512 (Div. 2) D.Vasya and Triangle 数学

Codeforces Round #423 (Div. 2, rated, based on VK Cup Finals) E. DNA Evolution 树状数组

Codeforces Round #754 (Div. 2)E 待写