经验首页 前端设计 程序设计 Java相关 移动开发 数据库/运维 软件/图像 大数据/云计算 其他经验
当前位置:技术经验 » 程序设计 » C++ » 查看文章
BZOJ4589: Hard Nim(FWT 快速幂)
来源:cnblogs  作者:自为风月马前卒  时间:2018/11/30 9:38:47  对本文有异议

题意

题目链接

Sol

神仙题Orzzzz

题目可以转化为从\(\leqslant M\)的质数中选出\(N\)\(xor\)和为\(0\)的方案数

这样就好做多了

\(f(x) = [x \text{是质数}]\)

\(n\)次异或FWT即可

快速幂优化一下,中间不用IFWT,最后转一次就行(然而并不知道为什么)

哪位大佬教教我这题的DP怎么写呀qwqqqq

死过不过去样例。。

  1. #include<bits/stdc++.h>
  2. using namespace std;
  3. const int MAXN = (1 << 17) + 10, mod = 998244353, inv2 = 499122177;
  4. inline int read() {
  5. char c = getchar(); int x = 0, f = 1;
  6. while(c < '0' || c > '9') {if(c == '-') f = -1; c = getchar();}
  7. while(c >= '0' && c <= '9') x = x * 10 + c - '0', c = getchar();
  8. return x * f;
  9. }
  10. int N, A[MAXN], B[MAXN], C[MAXN];
  11. int add(int x, int y) {
  12. if(x + y < 0) return x + y + mod;
  13. return x + y >= mod ? x + y - mod : x + y;
  14. }
  15. int mul(int x, int y) {
  16. return 1ll * x * y % mod;
  17. }
  18. void FWTor(int *a, int opt) {
  19. for(int mid = 1; mid < N; mid <<= 1)
  20. for(int R = mid << 1, j = 0; j < N; j += R)
  21. for(int k = 0; k < mid; k++)
  22. if(opt == 1) a[j + k + mid] = add(a[j + k], a[j + k + mid]);
  23. else a[j + k + mid] = add(a[j + k + mid], -a[j + k]);
  24. }
  25. void FWTand(int *a, int opt) {
  26. for(int mid = 1; mid < N; mid <<= 1)
  27. for(int R = mid << 1, j = 0; j < N; j += R)
  28. for(int k = 0; k < mid; k++)
  29. if(opt == 1) a[j + k] = add(a[j + k], a[j + k + mid]);
  30. else a[j + k] = add(a[j + k], -a[j + k + mid]);
  31. }
  32. void FWTxor(int *a, int opt) {
  33. for(int mid = 1; mid < N; mid <<= 1)
  34. for(int R = mid << 1, j = 0; j < N; j += R)
  35. for(int k = 0; k < mid; k++) {
  36. int x = a[j + k], y = a[j + k + mid];
  37. if(opt == 1) a[j + k] = add(x, y), a[j + k + mid] = add(x, -y);
  38. else a[j + k] = mul(add(x, y), inv2), a[j + k + mid] = mul(add(x, -y), inv2);
  39. }
  40. }
  41. int main() {
  42. N = 1 << (read());
  43. for(int i = 0; i < N; i++) A[i] = read();
  44. for(int i = 0; i < N; i++) B[i] = read();
  45. FWTor(A, 1); FWTor(B, 1);
  46. for(int i = 0; i < N; i++) C[i] = mul(A[i], B[i]);
  47. FWTor(C, -1); FWTor(A, -1); FWTor(B, -1);
  48. for(int i = 0; i < N; i++) printf("%d ", C[i]); puts("");
  49. FWTand(A, 1); FWTand(B, 1);
  50. for(int i = 0; i < N; i++) C[i] = mul(A[i], B[i]);
  51. FWTand(C, -1); FWTand(A, -1); FWTand(B, -1);
  52. for(int i = 0; i < N; i++) printf("%d ", C[i]); puts("");
  53. FWTxor(A, 1); FWTxor(B, 1);
  54. for(int i = 0; i < N; i++) C[i] = mul(A[i], B[i]);
  55. FWTxor(C, -1); FWTxor(A, -1); FWTxor(B, -1);
  56. for(int i = 0; i < N; i++) printf("%d ", C[i]);
  57. return 0;
  58. }
 友情链接:直通硅谷  点职佳  北美留学生论坛

本站QQ群:前端 618073944 | Java 606181507 | Python 626812652 | C/C++ 612253063 | 微信 634508462 | 苹果 692586424 | C#/.net 182808419 | PHP 305140648 | 运维 608723728

W3xue 的所有内容仅供测试,对任何法律问题及风险不承担任何责任。通过使用本站内容随之而来的风险与本站无关。
关于我们  |  意见建议  |  捐助我们  |  报错有奖  |  广告合作、友情链接(目前9元/月)请联系QQ:27243702 沸活量
皖ICP备17017327号-2 皖公网安备34020702000426号