牛顿迭代

\[G(F_0(x))\equiv 0(mod\ x^{2^t})
\]

牛顿迭代

\[F(x)\equiv F_0(x)-\frac{G(F_0(x))}{G'(F_0(x))}(mod\ x^{2^{t+1}})
\]

以下多数都可以牛顿迭代公式一步得到

多项式求逆

给定\(A(x)\)求满足\(A(x)*B(x)=1\)的\(B(x)\)

写成

\[A(x)*B(x)=1(mod \ x^n)
\]

我们会求$$A(x)*B(x)=1(mod \ x^1)$$

然后我们考虑求$$A(x)*B(x)=1(mod \ x^t)$$

\[(A(x)*B(x)-1)^2=0(mod \ x^{2t})
\]

\[A(x)(2B(x)-A(x)*B^2(x))=1(mod \ x^{2t})
\]

把\(2B(x)-A(x)*B^2(x)\)当作新的\(B\)倍增算

从\(mod \ x^1\)倍增到大于等于\(n\)

  1. # include <bits/stdc++.h>
  2. # define RG register
  3. # define IL inline
  4. # define Fill(a, b) memset(a, b, sizeof(a))
  5. using namespace std;
  6. typedef long long ll;
  7. const int _(4e5 + 5);
  8. const int Zsy(998244353);
  9. const int Phi(998244352);
  10. const int G(3);
  11. IL int Input(){
  12. RG int x = 0, z = 1; RG char c = getchar();
  13. for(; c < '0' || c > '9'; c = getchar()) z = c == '-' ? -1 : 1;
  14. for(; c >= '0' && c <= '9'; c = getchar()) x = (x << 1) + (x << 3) + (c ^ 48);
  15. return x * z;
  16. }
  17. IL int Pow(RG ll x, RG ll y){
  18. RG ll ret = 1;
  19. for(; y; x = x * x % Zsy, y >>= 1)
  20. if(y & 1) ret = ret * x % Zsy;
  21. return ret;
  22. }
  23. int N, r[_], l, A[_], B[_];
  24. IL void NTT(RG int *P, RG int opt){
  25. for(RG int i = 0; i < N; ++i) if(i < r[i]) swap(P[i], P[r[i]]);
  26. for(RG int i = 1; i < N; i <<= 1){
  27. RG int wn = Pow(G, Phi / (i << 1));
  28. if(opt == -1) wn = Pow(wn, Zsy - 2);
  29. for(RG int j = 0, p = i << 1; j < N; j += p)
  30. for(RG int w = 1, k = 0; k < i; w = 1LL * w * wn % Zsy, ++k){
  31. RG int X = P[k + j], Y = 1LL * w * P[k + j + i] % Zsy;
  32. P[k + j] = (X + Y) % Zsy, P[k + j + i] = (X - Y + Zsy) % Zsy;
  33. }
  34. }
  35. }
  36. IL void Mul(RG int *a, RG int *b, RG int len){
  37. for(l = 0, N = 1, len += len - 1; N <= len; N <<= 1) ++l;
  38. for(RG int i = 0; i < N; ++i) r[i] = (r[i >> 1] >> 1) | ((i & 1) << (l - 1));
  39. for(RG int i = 0; i < N; ++i) A[i] = B[i] = 0;
  40. for(RG int i = 0; i <= len >> 1; ++i) A[i] = a[i], B[i] = b[i];
  41. NTT(A, 1), NTT(B, 1);
  42. for(RG int i = 0; i < N; ++i) A[i] = 1LL * A[i] * B[i] % Zsy * B[i] % Zsy;
  43. NTT(A, -1);
  44. RG int inv = Pow(N, Zsy - 2);
  45. for(RG int i = 0; i <= len; ++i) A[i] = 1LL * A[i] * inv % Zsy;
  46. }
  47. int n, a[_], b[_], c[_], m;
  48. int main(RG int argc, RG char *argv[]){
  49. n = Input();
  50. for(RG int i = 0; i < n; ++i) a[i] = Input() % Zsy;
  51. for(m = 1; m < n; m <<= 1);
  52. b[0] = Pow(a[0], Zsy - 2);
  53. for(RG int t = 2; t <= m; t <<= 1){
  54. for(RG int i = 0; i < t; ++i) c[i] = b[i];
  55. Mul(a, b, t);
  56. for(RG int i = 0; i < t; ++i)
  57. b[i] = ((c[i] + c[i]) % Zsy - A[i] + Zsy) % Zsy;
  58. }
  59. for(RG int i = 0; i < n; ++i) printf("%d ", b[i]);
  60. return puts(""), 0;
  61. }

多项式除法

已知\(n\)次多项式\(A(x)\)和\(m\)次多项式\(B(x)\),\(n>m\)

求\(A(x)\)除以\(B(x)\)的商\(C(x)\)及余式\(D(x)\)

也就是

\[A(x)=B(x)C(x)+D(x)
\]

\[A(\frac{1}{x})=B(\frac{1}{x})C(\frac{1}{x})+D(\frac{1}{x})
\]

\[x^nA(\frac{1}{x})=(x^mB(\frac{1}{x}))(x^{n-m}C(\frac{1}{x}))+x^{n-m+1}(x^{n-1}D(\frac{1}{x}))
\]

对\(x^{n-m+1}\)取模

\[A^R(x)=B^R(x)C^R(x)(mod \ x^{n-m+1})
\]

\(R\)表示把系数倒置,即\(swap\)前后

那么可以多项式求逆,再相乘得到\(C^R(x)\)

然后去掉\(R\)带入原式相乘再相减得到\(D(x)\)

  1. # include <bits/stdc++.h>
  2. # define IL inline
  3. # define RG register
  4. # define Fill(a, b) memset(a, b, sizeof(a))
  5. using namespace std;
  6. typedef long long ll;
  7. IL int Input(){
  8. RG int x = 0, z = 1; RG char c = getchar();
  9. for(; c < '0' || c > '9'; c = getchar()) z = c == '-' ? -1 : 1;
  10. for(; c >= '0' && c <= '9'; c = getchar()) x = (x << 1) + (x << 3) + (c ^ 48);
  11. return x * z;
  12. }
  13. const int mod(998244353);
  14. const int phi(998244352);
  15. const int maxn(8e5 + 5);
  16. const int g(3);
  17. IL int Pow(RG ll x, RG ll y){
  18. RG ll ret = 1;
  19. for(; y; y >>= 1, x = x * x % mod)
  20. if(y & 1) ret = ret * x % mod;
  21. return ret;
  22. }
  23. int x[maxn], y[maxn], z[maxn], s[maxn], c[maxn], n, m, a[maxn], b[maxn], r[maxn], len;
  24. IL void NTT(RG int *p, RG int m, RG int opt){
  25. RG int l = 0, n = 1;
  26. for(; n < m; n <<= 1) ++l;
  27. for(RG int i = 0; i < n; ++i) r[i] = (r[i >> 1] >> 1) | ((i & 1) << (l - 1));
  28. for(RG int i = 0; i < n; ++i) if(r[i] < i) swap(p[r[i]], p[i]);
  29. for(RG int i = 1; i < n; i <<= 1){
  30. RG int wn = Pow(g, phi / (i << 1));
  31. if(opt == -1) wn = Pow(wn, mod - 2);
  32. for(RG int j = 0, t = i << 1; j < n; j += t)
  33. for(RG int k = 0, w = 1; k < i; ++k, w = 1LL * w * wn % mod){
  34. RG int x = p[j + k], y = 1LL * w * p[j + k + i] % mod;
  35. p[j + k] = (x + y) % mod, p[j + k + i] = (x - y + mod) % mod;
  36. }
  37. }
  38. if(opt == -1){
  39. RG int inv = Pow(n, mod - 2);
  40. for(RG int i = 0; i < n; ++i) p[i] = 1LL * p[i] * inv % mod;
  41. }
  42. }
  43. IL void Inv(RG int *p, RG int *q, RG int num){
  44. if(num == 1){
  45. q[0] = Pow(p[0], mod - 2);
  46. return;
  47. }
  48. Inv(p, q, num >> 1);
  49. for(RG int i = 0; i < num; ++i) a[i] = p[i], b[i] = q[i];
  50. RG int l = num << 1;
  51. NTT(a, l, 1), NTT(b, l, 1);
  52. for(RG int i = 0; i < l; ++i) a[i] = 1LL * a[i] * b[i] % mod * b[i] % mod;
  53. NTT(a, l, -1);
  54. for(RG int i = 0; i < num; ++i) q[i] = ((2 * q[i] - a[i]) % mod + mod) % mod;
  55. for(RG int i = 0; i < l; ++i) a[i] = b[i] = 0;
  56. }
  57. int main(){
  58. n = Input(), m = Input();
  59. for(RG int i = 0; i <= n; ++i) y[i] = Input();
  60. for(RG int i = 0; i <= m; ++i) x[i] = Input();
  61. reverse(x, x + m + 1), reverse(y, y + n + 1);
  62. for(RG int i = 0; i <= n - m; ++i) s[i] = x[i];
  63. for(len = 1; len <= n - m; len <<= 1);
  64. Inv(s, z, len);
  65. for(len = 1; len <= (n - m) << 1; len <<= 1);
  66. for(RG int i = 0; i <= n - m; ++i) a[i] = y[i];
  67. for(RG int i = 0; i <= n - m; ++i) b[i] = z[i];
  68. len <<= 1;
  69. NTT(a, len, 1), NTT(b, len, 1);
  70. for(RG int i = 0; i < len; ++i) b[i] = 1LL * b[i] * a[i] % mod;
  71. NTT(b, len, -1), reverse(b, b + n - m + 1);
  72. for(RG int i = 0; i <= n - m; ++i) c[i] = b[i], printf("%d ", c[i]);
  73. puts(""), reverse(y, y + n + 1), reverse(x, x + m + 1);
  74. for(RG int i = 0; i < len; ++i) a[i] = b[i] = 0;
  75. for(len = 1; len <= n; len <<= 1);
  76. for(RG int i = 0; i <= n; ++i) a[i] = x[i];
  77. for(RG int i = 0; i <= n - m; ++i) b[i] = c[i];
  78. NTT(a, len, 1), NTT(b, len, 1);
  79. for(RG int i = 0; i < len; ++i) a[i] = 1LL * a[i] * b[i] % mod;
  80. NTT(a, len, -1);
  81. for(RG int i = 0; i < m; ++i) y[i] = (y[i] - a[i] + mod) % mod, printf("%d ", y[i]);
  82. return 0;
  83. }

多项式开方

给定\(B(x)\),求\(A(x)\)使\(A^2(x)=B(x)\)

写成

\[A^2(x)=B(x) (mod \ x^n)
\]

然后

\[A^2(x)=B(x)(mod \ x^1)
\]

是可以求的,好像是什么二次剩余

留坑在这里以后补

考虑求

\[A^2(x)=B(x)(mod \ x^{2t})
\]

\[C^2(x)=B(x)(mod \ x^t)
\]

那么

\[(A^2(x)-C^2(x))^2=0(mod \ x^{2t})
\]

\[A^4(x)-2A^2(x)C^2(x)+C^$(x)=0(mod \ x^{2t})
\]

\[A^2(x)=\frac{A^4(x)+C^4(x)}{2C^2(x)}(mod \ x^{2t})
\]

\[2A^2(x)=\frac{A^4(x)+2C^2(x)A^2(x)+C^4(x)}{2C^2(x)}(mod \ x^{2t})
\]

\[A^2(x)=\frac{(A^2(x)+C^2(x))^2}{(2C(x))^2}(mod \ x^{2t})
\]

\[A(x)=\frac{B(x)+C^2(x)}{2C(x)}(mod \ x^{2t})
\]

同样的还是倍增求

多项式ln

设\(B(x)=ln(A(x))\)

同时求导

就是

\[B'(x)=\frac{A'(x)}{A(x)}
\]

那么多项式求导,然后多项式求逆,然后多项式积分就好了

多项式exp

设\(B(x)=e^{A(x)}\)

那么

\[ln(B(x))=A(x)
\]

牛顿迭代

\[B(x)(mod\ 2^{t+1})=B(x)(mod\ 2^t)(1-ln(B(x)(mod\ 2^t))+A(x))
\]

多项式求幂

设\(B(x)=A^k(x)\)

那么\(ln(B(x))=kln(A(x))\)

然后就是求\(ln\)然后\(exp\)就好了

模板!!!

COGS2189. [HZOI 2015] 帕秋莉的超级多项式

  1. # include <bits/stdc++.h>
  2. # define RG register
  3. # define IL inline
  4. # define Fill(a, b) memset(a, b, sizeof(a))
  5. using namespace std;
  6. typedef long long ll;
  7. IL int Input(){
  8. RG int x = 0, z = 1; RG char c = getchar();
  9. for(; c < '0' || c > '9'; c = getchar()) z = c == '-' ? -1 : 1;
  10. for(; c >= '0' && c <= '9'; c = getchar()) x = (x << 1) + (x << 3) + (c ^ 48);
  11. return x * z;
  12. }
  13. const int maxn(8e5 + 5);
  14. const int mod(998244353);
  15. const int phi(998244352);
  16. const int inv2(499122177);
  17. const int g(3);
  18. int a[maxn], b[maxn], c[maxn], d[maxn], r[maxn];
  19. IL int Pow(RG ll x, RG ll y){
  20. RG ll ret = 1;
  21. for(; y; y >>= 1, x = x * x % mod)
  22. if(y & 1) ret = ret * x % mod;
  23. return ret;
  24. }
  25. IL void NTT(RG int *p, RG int m, RG int opt){
  26. RG int n = 1, l = 0;
  27. for(; n < m; n <<= 1) ++l;
  28. for(RG int i = 0; i < n; ++i) r[i] = (r[i >> 1] >> 1) | ((i & 1) << (l - 1));
  29. for(RG int i = 0; i < n; ++i) if(r[i] < i) swap(p[i], p[r[i]]);
  30. for(RG int i = 1; i < n; i <<= 1){
  31. RG int t = i << 1, wn = Pow(g, phi / t);
  32. if(opt == -1) wn = Pow(wn, mod - 2);
  33. for(RG int j = 0; j < n; j += t)
  34. for(RG int k = 0, w = 1; k < i; ++k, w = 1LL * w * wn % mod){
  35. RG int x = p[k + j], y = 1LL * w * p[k + j + i] % mod;
  36. p[k + j] = (x + y) % mod, p[k + j + i] = (x - y + mod) % mod;
  37. }
  38. }
  39. if(opt == -1){
  40. RG int inv = Pow(n, mod - 2);
  41. for(RG int i = 0; i < n; ++i) p[i] = 1LL * p[i] * inv % mod;
  42. }
  43. }
  44. IL void Inv(RG int *p, RG int *q, RG int len){
  45. if(len == 1){
  46. q[0] = Pow(p[0], mod - 2);
  47. return;
  48. }
  49. Inv(p, q, len >> 1);
  50. for(RG int i = 0; i < len; ++i) a[i] = p[i], b[i] = q[i];
  51. RG int tmp = len << 1;
  52. NTT(a, tmp, 1), NTT(b, tmp, 1);
  53. for(RG int i = 0; i < tmp; ++i) a[i] = 1LL * a[i] * b[i] % mod * b[i] % mod;
  54. NTT(a, tmp, -1);
  55. for(RG int i = 0; i < len; ++i) q[i] = ((2 * q[i] - a[i]) % mod + mod) % mod;
  56. for(RG int i = 0; i < tmp; ++i) a[i] = b[i] = 0;
  57. }
  58. IL void Sqrt(RG int *p, RG int *q, RG int len){
  59. if(len == 1){
  60. q[0] = sqrt(p[0]); //???
  61. return;
  62. }
  63. Sqrt(p, q, len >> 1), Inv(q, c, len);
  64. RG int tmp = len << 1;
  65. for(RG int i = 0; i < len; ++i) a[i] = p[i];
  66. NTT(a, tmp, 1), NTT(c, tmp, 1);
  67. for(RG int i = 0; i < tmp; ++i) a[i] = 1LL * a[i] * c[i] % mod;
  68. NTT(a, tmp, -1);
  69. for(RG int i = 0; i < len; ++i) q[i] = 1LL * (q[i] + a[i]) % mod * inv2 % mod;
  70. for(RG int i = 0; i < tmp; ++i) a[i] = c[i] = 0;
  71. }
  72. IL void ICalc(RG int *p, RG int *q, RG int len){
  73. q[len - 1] = 0;
  74. for(RG int i = 1; i < len; ++i) q[i - 1] = 1LL * p[i] * i % mod;
  75. }
  76. IL void Calc(RG int *p, RG int *q, RG int len){
  77. q[0] = 0;
  78. for(RG int i = 1; i < len; ++i) q[i] = 1LL * Pow(i, mod - 2) * p[i - 1] % mod;
  79. }
  80. IL void Ln(RG int *p, RG int *q, RG int len){
  81. Inv(p, c, len), ICalc(p, a, len);
  82. RG int tmp = len << 1;
  83. NTT(c, tmp, 1), NTT(a, tmp, 1);
  84. for(RG int i = 0; i < tmp; ++i) c[i] = 1LL * c[i] * a[i] % mod;
  85. NTT(c, tmp, -1), Calc(c, q, len);
  86. for(RG int i = 0; i < tmp; ++i) a[i] = c[i] = 0;
  87. }
  88. IL void Exp(RG int *p, RG int *q, RG int len){
  89. if(len == 1){
  90. q[0] = 1;
  91. return;
  92. }
  93. Exp(p, q, len >> 1), Ln(q, b, len);
  94. for(RG int i = 0; i < len; ++i) b[i] = (mod - b[i] + p[i]) % mod, c[i] = q[i];
  95. b[0] = (b[0] + 1) % mod;
  96. RG int tmp = len << 1;
  97. NTT(b, tmp, 1), NTT(c, tmp, 1);
  98. for(RG int i = 0; i < tmp; ++i) b[i] = 1LL * b[i] * c[i] % mod;
  99. NTT(b, tmp, -1);
  100. for(RG int i = 0; i < len; ++i) q[i] = b[i];
  101. for(RG int i = 0; i < tmp; ++i) b[i] = c[i] = 0;
  102. }
  103. IL void CalcPow(RG int *p, RG int *q, RG int len, RG int y){
  104. Ln(p, d, len);
  105. for(RG int i = 0; i < len; ++i) d[i] = 1LL * d[i] * y % mod;
  106. Exp(d, q, len);
  107. for(RG int i = 0; i < len; ++i) d[i] = 0;
  108. }
  109. int f[maxn], h[maxn], n, k, len;
  110. IL void Record(){
  111. for(RG int i = 0; i < len; ++i) f[i] = h[i], h[i] = 0;
  112. }
  113. int main(){
  114. freopen("polynomial.in", "r", stdin);
  115. freopen("polynomial.out", "w", stdout);
  116. n = Input() - 1, k = Input();
  117. for(RG int i = 0; i <= n; ++i) f[i] = Input();
  118. for(len = 1; len <= n; len <<= 1);
  119. Sqrt(f, h, len), Record();
  120. Inv(f, h, len), Record();
  121. Calc(f, h, n + 1), Record();
  122. Exp(f, h, len), Record();
  123. Inv(f, h, len), Record();
  124. f[0] = (f[0] + 1) % mod;
  125. Ln(f, h, len), Record();
  126. f[0] = (f[0] + 1) % mod;
  127. CalcPow(f, h, len, k), Record();
  128. ICalc(f, h, n + 1);
  129. for(RG int i = 0; i <= n; ++i) printf("%d ", h[i]);
  130. return 0;
  131. }

牛顿迭代,多项式求逆,除法,开方,exp,ln,求幂的更多相关文章

  1. [模板] 多项式: 乘法/求逆/分治fft/微积分/ln/exp/幂

    多项式 代码 const int nsz=(int)4e5+50; const ll nmod=998244353,g=3,ginv=332748118ll; //basic math ll qp(l ...

  2. luogu P4726 多项式指数函数(模板题FFT、多项式求逆、多项式对数函数)

    手动博客搬家: 本文发表于20181127 08:39:42, 原地址https://blog.csdn.net/suncongbo/article/details/84559818 题目链接: ht ...

  3. 树状数组求逆序对:POJ 2299、3067

    前几天开始看树状数组了,然后开始找题来刷. 首先是 POJ 2299 Ultra-QuickSort: http://poj.org/problem?id=2299 这题是指给你一个无序序列,只能交换 ...

  4. [CF 351B]Jeff and Furik[归并排序求逆序数]

    题意: 两人游戏, J先走. 给出一个1~n的排列, J选择一对相邻数[题意!!~囧], 交换. F接着走, 扔一硬币, 若正面朝上, 随机选择一对降序排列的相邻数, 交换. 若反面朝上, 随机选择一 ...

  5. Ultra-QuickSort(树状数组求逆序对数)

    Ultra-QuickSort 题目链接:http://poj.org/problem?id=2299 Time Limit: 7000MS   Memory Limit: 65536K Total ...

  6. 求逆序对常用的两种算法 ----归并排 & 树状数组

    网上看了一些归并排求逆序对的文章,又看了一些树状数组的,觉得自己也写一篇试试看吧,然后本文大体也就讲个思路(没有例题),但是还是会有个程序框架的 好了下面是正文 归并排求逆序对 树状数组求逆序对 一. ...

  7. 求逆序对 ----归并排 & 树状数组

    网上看了一些归并排求逆序对的文章,又看了一些树状数组的,觉得自己也写一篇试试看吧,然后本文大体也就讲个思路(没有例题),但是还是会有个程序框架的 好了下面是正文 归并排求逆序对 树状数组求逆序对 一. ...

  8. 51 Nod 1107 斜率小于0的连线数量 (转换为归并求逆序数或者直接树状数组,超级详细题解!!!)

    1107 斜率小于0的连线数量 基准时间限制:1 秒 空间限制:131072 KB 分值: 40 难度:4级算法题   二维平面上N个点之间共有C(n,2)条连线.求这C(n,2)条线中斜率小于0的线 ...

  9. 多项式的各类计算(多项式的逆/开根/对数/exp/带余除法/多点求值)

    预备知识:FFT/NTT 多项式的逆 给定一个多项式 F(x)F(x)F(x),请求出一个多项式 G(x)G(x)G(x),满足 F(x)∗G(x)≡1(mod xn)F(x)*G(x) \equiv ...

随机推荐

  1. 使用vue+webpack从零搭建项目

    vue到现在已经成为一个热门的框架,在项目实践当中,如果想要创建一个新项目,通常都会使用vue-cli的脚手架工具,毋容置疑能够方便很多,很多东西也不需要自己亲自去配置.都知道,脚手架其实是vue结合 ...

  2. HEOI2019游记(退役记)

    少了回程铁路相关信息,有空补 AFO 辣鸡蒟蒻ghj1222顺利地退役了 由于没带手机拍照片,本次坐动车不写运转记录,下次去CTS/APIO应该是坐普速车,应该能带手机拍照,应该会写运转记录 Day ...

  3. Windows下安装Redis服务(zip)

    1.官方没有 Windows版本的 Redis,官网介绍: Redis项目不正式支持Windows.但是,微软开发并维护了针对Win64的Windows版本. 2.Windows版本下载地址:http ...

  4. iis上部署本地数据库LocalDB的方法

    1. iis应用程序池的标识设置为"ApplicationPoolIdentify"(比较安全) 2. 不要将数据库物理文件保存在网站的物理路径内,因为iis应用程序池的标识为Ap ...

  5. Jenkins 发布平台 MSB4064: The "Retries" parameter is not supported & error MSB4063: The "Copy" task could not be initialized

    ____________________________________________________________________________________________________ ...

  6. vue使用nprogress页面加载进度条

    vue使用nprogress页面加载进度条 NProgress是页面跳转是出现在浏览器顶部的进度条 官网:http://ricostacruz.com/nprogress/ github:https: ...

  7. mysql语句插入前判断数据是否重复

    在mysql中插入数据有时需要判断数据插入是否重复 语句编写:insert into 表(相应字段) select 相应字段 from dual where not exists (select 相应 ...

  8. Linux 系统下安装 mysql5.7.25(glibc版)

    前言:经过一天半的折腾,终于把 mysql 5.7.25 版本安装上了 Amazon Linux AMI release 2017.09 系统上,把能参考的博客几乎都看了一遍,终于发现这些细节问题,然 ...

  9. 3dsmax2020卸载/安装失败/如何彻底卸载清除干净3dsmax2020注册表和文件的方法

    3dsmax2020提示安装未完成,某些产品无法安装该怎样解决呢?一些朋友在win7或者win10系统下安装3dsmax2020失败提示3dsmax2020安装未完成,某些产品无法安装,也有时候想重新 ...

  10. 如何获取select中的value、text、index相关值 && 如何获取单选框中radio值 && 触发事件 && radio 默认选中

    如何获取select中的value.text.index相关值 select还是比较常用的一个标签,如何获取其中的内容呢? 如下所示: <select id="select" ...