2018.12.30 洛谷P4238 【模板】多项式求逆
传送门
多项式求逆模板题。
简单讲讲?
多项式求逆
- 定义:
对于一个多项式A(x)A(x)A(x),如果存在一个多项式B(x)B(x)B(x),满足B(x)B(x)B(x)的次数小于等于A(x)A(x)A(x)且A(x)B(x)≡1mod  xnA(x)B(x)≡1 \mod x^nA(x)B(x)≡1modxn,那么我们称B(x)为A(x)A(x)A(x)在模xnx^nxn意义下的逆元,简单记作A−1(x)A^{−1}(x)A−1(x) - 求法:
n=1?n=1?n=1?那不就是ccc的逆元么。
n>1?n>1?n>1?我们令B(x)=A−1(x)B(x)=A^{-1}(x)B(x)=A−1(x)
那么有A(x)B(x)≡1mod  xnA(x)B(x)\equiv 1 \mod x^nA(x)B(x)≡1modxn
然后可以用类似倍增的方法求。
假设我们已经知道C(x)C(x)C(x)满足A(x)C(x)≡1mod  xn2A(x)C(x)\equiv 1\mod x^{\frac n2}A(x)C(x)≡1modx2n(这里的n2\frac n22n都是向上取整)
显然A(x)B(x)≡1mod  xn2A(x)B(x)\equiv 1\mod x^{\frac n2}A(x)B(x)≡1modx2n是成立的。
我们将两式相减:
A(x)(B(x)−C(x))≡0mod  xn2A(x)(B(x)-C(x))\equiv 0\mod x^{\frac n2}A(x)(B(x)−C(x))≡0modx2n
所以B(x)−C(x)≡0mod  xn2B(x)-C(x)\equiv 0\mod x^{\frac n2}B(x)−C(x)≡0modx2n
然后将两边平方:
B2(x)−2B(x)C(x)+C2(x)≡0mod  xn2B^2(x)-2B(x)C(x)+C^2(x)\equiv 0\mod x^{\frac n2}B2(x)−2B(x)C(x)+C2(x)≡0modx2n
=>B2(x)−2B(x)C(x)+C2(x)≡0mod  xnB^2(x)-2B(x)C(x)+C^2(x)\equiv 0\mod x^nB2(x)−2B(x)C(x)+C2(x)≡0modxn
这一步很关键,请神犇们仔细思考原因
然后两边同时乘上A(x)A(x)A(x)
=>B(x)−2C(x)+A(x)C2(x)≡0mod  xn)B(x)-2C(x)+A(x)C^2(x)\equiv 0\mod x^n)B(x)−2C(x)+A(x)C2(x)≡0modxn)
于是B(x)≡2C(x)−A(x)C2(x)mod  xnB(x)\equiv2C(x)-A(x)C^2(x)\mod x^nB(x)≡2C(x)−A(x)C2(x)modxn
乘法可以用fft/nttfft/nttfft/ntt加速,因为每次递归的时候多项式最高次项都减少一半,所以总复杂度仍然是O(nlogn)O(nlogn)O(nlogn)
代码:
#include<bits/stdc++.h>
#define ri register int
using namespace std;
inline int read(){
int ans=0;
char ch=getchar();
while(!isdigit(ch))ch=getchar();
while(isdigit(ch))ans=(ans<<3)+(ans<<1)+(ch^48),ch=getchar();
return ans;
}
typedef long long ll;
const int mod=998244353;
int n;
inline int ksm(int a,int p){int ret=1;for(;p;p>>=1,a=(ll)a*a%mod)if(p&1)ret=(ll)ret*a%mod;return ret;}
inline int add(const int&a,const int&b){return a+b>=mod?a+b-mod:a+b;}
inline int dec(const int&a,const int&b){return a>=b?a-b:a-b+mod;}
inline int mul(const int&a,const int&b){return (ll)a*b%mod;}
int lim,tim;
vector<int>pos,A,B;
inline void init(const int&n){lim=1,tim=0;
while(lim<=n)lim<<=1,++tim;
pos.resize(lim),pos[0]=0;
for(ri i=0;i<lim;++i)pos[i]=(pos[i>>1]>>1)|((i&1)<<(tim-1));
}
inline void ntt(vector<int>&a,int type){
for(ri i=0;i<lim;++i)if(i<pos[i])swap(a[i],a[pos[i]]);
for(ri mult=(mod-1)/2,mid=1,wn,typ=type==1?3:(mod+1)/3;mid<lim;mid<<=1,mult>>=1){
wn=ksm(typ,mult);
for(ri j=0,len=mid<<1,w;j<lim;j+=len){
w=1;
for(ri k=0,a0,a1;k<mid;w=mul(w,wn),++k){
a0=a[j+k],a1=mul(w,a[j+k+mid]);
a[j+k]=add(a0,a1),a[j+k+mid]=dec(a0,a1);
}
}
}
if(type==-1)for(ri i=0,inv=ksm(lim,mod-2);i<lim;++i)a[i]=mul(a[i],inv);
}
struct poly{
vector<int>a;
poly(const int&n,int x=0){a.resize(n+1),a[n]=x;}
inline int&operator[](const int&i){return a[i];}
inline const int&operator[](const int&i)const{return a[i];}
inline poly extend(const int&x){poly ret=*this;return ret.a.resize(x),ret;}
inline int deg()const{return a.size()-1;}
friend inline poly operator+(const poly&a,const poly&b){
poly c(max(a.deg(),b.deg()));
for(ri i=0;i<=a.deg();++i)c[i]=add(c[i],a[i]);
for(ri i=0;i<=b.deg();++i)c[i]=add(c[i],b[i]);
return c;
}
friend inline poly operator-(const poly&a,const poly&b){
poly c(max(a.deg(),b.deg()));
for(ri i=0;i<=a.deg();++i)c[i]=add(c[i],a[i]);
for(ri i=0;i<=b.deg();++i)c[i]=dec(c[i],b[i]);
return c;
}
friend inline poly operator*(const poly&a,const int&b){
poly c=a;
for(ri i=0;i<=c.deg();++i)c[i]=mul(b,c[i]);
return c;
}
friend inline poly operator *(const poly&a,const poly&b){
int n=a.deg(),m=b.deg();
init(n+m),A.resize(lim),B.resize(lim);
poly ret(lim-1);
for(ri i=0;i<=n;++i)A[i]=a[i];
for(ri i=0;i<=m;++i)B[i]=b[i];
for(ri i=n+1;i<lim;++i)A[i]=0;
for(ri i=m+1;i<lim;++i)B[i]=0;
ntt(A,1),ntt(B,1);
for(ri i=0;i<lim;++i)A[i]=mul(A[i],B[i]);
return ntt(A,-1),ret.a=A,ret;
}
inline poly poly_inv(poly A,const int k){
if(k==1)return poly(0,ksm(A[0],mod-2));
poly f0=poly_inv(A.extend((k+1)>>1),(k+1)>>1);
return (f0*2-(A*((f0*f0).extend(k))).extend(k)).extend(k);
}
};
int main(){
freopen("lx.in","r",stdin);
n=read()-1;
poly a(n);
for(ri i=0;i<=n;++i)a[i]=read();
init(n*2),a=a.extend(lim),a=a.poly_inv(a,lim);
for(ri i=0;i<=n;++i)cout<<a[i]<<' ';
return 0;
}
2018.12.30 洛谷P4238 【模板】多项式求逆的更多相关文章
- 洛谷 P4238 [模板] 多项式求逆
题目:https://www.luogu.org/problemnew/show/P4238 看博客:https://www.cnblogs.com/xiefengze1/p/9107752.html ...
- 多项式求逆元详解+模板 【洛谷P4238】多项式求逆
概述 多项式求逆元是一个非常重要的知识点,许多多项式操作都需要用到该算法,包括多项式取模,除法,开跟,求ln,求exp,快速幂.用快速傅里叶变换和倍增法可以在$O(n log n)$的时间复杂度下求出 ...
- 洛谷.4238.[模板]多项式求逆(NTT)
题目链接 设多项式\(f(x)\)在模\(x^n\)下的逆元为\(g(x)\) \[f(x)g(x)\equiv 1\ (mod\ x^n)\] \[f(x)g(x)-1\equiv 0\ (mod\ ...
- 【洛谷4238】 多项式求逆(NTT,分治)
前言 多项式求逆还是爽的一批 Solution 考虑分治求解这个问题. 直接每一次NTT一下就好了. 代码实现 #include<stdio.h> #include<stdlib.h ...
- 洛谷.3803.[模板]多项式乘法(FFT)
题目链接:洛谷.LOJ. FFT相关:快速傅里叶变换(FFT)详解.FFT总结.从多项式乘法到快速傅里叶变换. 5.4 又看了一遍,这个也不错. 2019.3.7 叕看了一遍,推荐这个. #inclu ...
- 洛谷.3803.[模板]多项式乘法(NTT)
题目链接:洛谷.LOJ. 为什么和那些差那么多啊.. 在这里记一下原根 Definition 阶 若\(a,p\)互质,且\(p>1\),我们称使\(a^n\equiv 1\ (mod\ p)\ ...
- 洛谷.4512.[模板]多项式除法(NTT)
题目链接 多项式除法 & 取模 很神奇,记录一下. 只是主要部分,更详细的和其它内容看这吧. 给定一个\(n\)次多项式\(A(x)\)和\(m\)次多项式\(D(x)\),求\(deg(Q) ...
- 洛谷 P4512 [模板] 多项式除法
题目:https://www.luogu.org/problemnew/show/P4512 看博客:https://www.cnblogs.com/owenyu/p/6724611.html htt ...
- 洛谷P4238【模板】多项式求逆
洛谷P4238 多项式求逆:http://blog.miskcoo.com/2015/05/polynomial-inverse 注意:直接在点值表达下做$B(x) \equiv 2B'(x) - A ...
随机推荐
- IE浏览器调试工具不能使用
Mac 使用VMware Fusion虚拟机,安装Windows 7 Service Pack 1 (SP1). 移除自带的IE8,下载并安装IE11(64位). IE 11 调试工具不能使用,并且调 ...
- CountDownLatch的和CyclicBarrier使用
CyclicBarrier的使用: 假设只有一个场景:每个线程代表一个跑步运动员,当运动员都准备好后,才一起出发,只要有一个人没有准备好,大家都等待. CountDownLacth使用: 他经常用于监 ...
- robotium—只有apk文件的测试
把ppt的内容总结一下,并把问题说明一下: 把基本步骤搞出来,用notepad的程序吧,直接安装apk,就当做是不知道源码就好啦! 直接用自己的手机上就行啦!! 一.重签名: 步骤: 1.直接运行re ...
- HDU 1255 覆盖的面积(线段树面积并)
描述 给定平面上若干矩形,求出被这些矩形覆盖过至少两次的区域的面积. Input 输入数据的第一行是一个正整数T(1<=T<=100),代表测试数据的数量.每个测试数据的第一行是一个正 ...
- java测试感受
这个星期四下午来了一次Java考试,用来测试在暑假自学Java的学习情况,不得不说这次考试十分的成功,把我对这学期的学习信心打击的很难受,我也知道这是我应得的教训,我也对我的专业水平有了很深刻的了解了 ...
- nginx安装扩展 sub_filter&http_ssl_module
nginx之所以轻,因为默认没有安装各种各样的扩展: nginx安装扩展插件: 下面列出两个可能会用到的插件 一.sub_filter内容过滤器,这个在nginx做http转发的时候会很常用 1.下载 ...
- activity背景毛玻璃效果
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools= ...
- three.map.control
网址:https://github.com/anvaka/three.map.control 在threejs群里发现的一个很有意思的问题之前没有接触过: 存在的问题: 我在微信小游戏中,用orbi ...
- Java开发MIS系统需要的技术及其作用
1.后台框架部分,常用spring.struts2(Struts2框架,提供了一种基于MVC体系结构的工程序的开发方法,具有组件模块化.灵活性和重用性等优点,使基于MVC模式的程序结构更加清晰,同时也 ...
- PAT 1076 Wifi密码(15)(代码)
1076 Wifi密码(15 分) 下面是微博上流传的一张照片:"各位亲爱的同学们,鉴于大家有时需要使用 wifi,又怕耽误亲们的学习,现将 wifi 密码设置为下列数学题答案:A-1:B- ...