题意:输出第x天 从n中选x个数进行异或的 和
思路:看到异或 一般与二进制有关系 剩下就是记录二进制的个数然后用组合数学就可以搞定了
代码:
#include <iostream>
#include <cstring>
#define rep(i,o,u) for(int i=o;i<=u;++i)
using namespace std;
typedef long long ll;
const int mod=1e6+3;
int c[1100][1100];ll cnt=0;
int data[1100];
int w[40];
int n;
void init(){
c[0][0]=1;
rep(i,1,1000){
rep(j, 0, i){
if (j==0||j==i) {
c[i][j]=1;
}
else {
c[i][j]=(c[i-1][j-1]+c[i-1][j])%mod;
}
}
}
}
void qw(int a){
int t=0;
while (a) {
if (a&1) {
++w[t];
}
++t;
a>>=1;
}
}
void solve(){
memset(w, 0, sizeof(w));
rep(i, 0, n-1){
scanf("%d",&data[i]);
qw(data[i]);
}
rep(i,1,n){
int sum=0;
rep(j, 0, 32){
int tmp=0;
for (int k=1; k<=i&&k<=w[j]; k+=2) {
tmp=(tmp+((ll)(1<<j)%mod)*((ll)c[w[j]][k]*c[n-w[j]][i-k])%mod)%mod;
}
sum=(sum+tmp)%mod;
}
if(i==n) cout<<sum<<endl;
else cout<<sum<<" ";
}
}
void debug(){
ll da[1100]={0};
cnt=1<<n;
cout<<endl;
rep(j, 1, cnt-1){
ll t=0;
int num=0;
rep(k, 0, n-1){
if((1<<k)>j)
break;
if ((1<<k)&j) {
++num;
t=t^data[k];
}
}
da[num]=(da[num]+t%mod)%mod;
}
rep(i, 1, n)
if(i==n) cout<<da[i]<<endl;
else cout<<da[i]<<" ";
}
int main(int argc, const char * argv[])
{
init();
while(scanf("%d",&n)==1)
{
solve();
// debug();
}
return 0;
}