hdu 6129 Just do it

来源:互联网 发布:加密视频破解软件 编辑:程序博客网 时间:2024/04/28 02:26

题意

Just do it
有一个长度为 n 的整数序列 {an},对其做 m 次前缀异或和,求最终的序列。

题解

对这个过程手动模拟几行,注意不要消去,可以发现第 m 次第 i 个数的结果包含了 Cijm1+ij 次第 j 个数(ji) 。

首先我们需要判断它的奇偶性。奇偶性相当于2进制的结果,2为质数,可以使用Lucas定理。2进制的每一位只有四种情况,其中 C10=0C00=C01=C11=1

m1ij 的每一位展开,在第 k 位上,如果 m1ij 都是 1,那么结果就是 0 。

从小到大枚举 k ,表示 ij 的第 k 位为 1,若 m1 的第 k 位不为 1,那么直接更新a序列本身。也就是说,每次只用满足 ij=2ka[j] 更新 a[i],然而此时的 a[j] 已经被 k0k1 更新过了,所以相当于考虑了 ij0k 位的所有情况。

代码

#include <bits/stdc++.h>using namespace std;const int N=2e5+5;int a[N];int main(){    int T,n,m;    scanf("%d",&T);    while (T--) {        scanf("%d%d",&n,&m);        for (int i=1;i<=n;i++) {            scanf("%d",a+i);        }        int k=1;m--;        while (k<n) {            if ((m&1)==0) {                for (int i=n;i>k;i--) {                    a[i]^=a[i-k];                }            }            m>>=1;k<<=1;        }        for (int i=1;i<=n;i++) {            printf("%d%c",a[i]," \n"[i==n]);        }    }    return 0;}
原创粉丝点击