//这个规律我服
#include <iostream>
#include <algorithm>
#include <stdio.h> #include <set> #include <queue> #include <limits.h> #include <string.h> #include <vector> #include <map> #include <math.h> #define LL long long #define INF 2100000000 #define fi first #define se second #define lowbit(x) (x&(-x)) #define eps 5e-7 using namespace std; const int maxn=(int)2e5 +30; const int MOD=998244353; int a[maxn]; #define judg(n,k) n&k==k int main(){ #ifdef shuaishuai freopen("C:\Users\hasee\Desktop\a.txt","r",stdin); //freopen("C:\Users\hasee\Desktop\b.txt","w",stdout); #endif int t,n,m; scanf("%d",&t); while(t-- ){ scanf("%d%d",&n,&m); for(int i=0;i<n;i++)scanf("%d",a+i); for(int k=0;1<<k<=m;k++){ if(m>>k&1){ printf("fuck:%d ",1<<k); for(int i=1<<k;i<n;i++){ a[i]^=a[i-(1<<k)]; printf("%d %d ",i,i-(1<<k)); } } } for(int i=0;i<n-1;i++)printf("%d ",a[i]);printf("%d ",a[n-1]); } // int t=15; // while(t){ // printf("t: %d lowbit :%d ",t,lowbit(t)); // t-=lowbit(t); // } return 0; }
x姐的话:
ftiasch(826513189) 2017-08-15 17:14:13
这个 dp[i][j] = dp[i - 1][j] + dp[i][j - 1]
ftiasch(826513189) 2017-08-15 17:14:33查看前后消息
你把这个式子写两遍。。。就会发现变成了
dp[i][j] = dp[i - 2][j] + 2 * dp[i - 1][j - 1] + dp[i][j - 2]
ftiasch(826513189) 2017-08-15 17:14:46
因为你 mod 2。。。所以中间那项不见了
ftiasch(826513189) 2017-08-15 17:14:50
再写两遍。。。
ftiasch(826513189) 2017-08-15 17:15:03
就会变成。。。dp[i][j] = dp[i - 2^k][j] + dp[i][j - 2^k] 这个样子。。。
ftiasch(826513189) 2017-08-15 17:15:13
所以你可以一次做 2^k 轮。。。
ftiasch(826513189) 2017-08-15 17:15:17
做 O(log m) 次就可以了。。。
我找到了这个不错的题解:
http://www.cnblogs.com/cmmdc/p/7371746.html