多项式全家桶

Include

多项式乘法

多项式求逆

多项式除法

多项式取模

多项式对数函数

多项式指数函数

多项式正弦函数

多项式余弦函数

#include<bits/stdc++.h>
#define reg register int
#define il inline
#define fi first
#define se second
#define mk(a,b) make_pair(a,b)
#define numb (ch^‘0‘)
using namespace std;
typedef long long ll;
template<class T>il void rd(T &x){
    char ch;x=0;bool fl=false;
    while(!isdigit(ch=getchar()))(ch==‘-‘)&&(fl=true);
    for(x=numb;isdigit(ch=getchar());x=x*10+numb);
    (fl==true)&&(x=-x);
}
template<class T>il void output(T x){if(x/10)output(x/10);putchar(x%10+‘0‘);}
template<class T>il void ot(T x){if(x<0) putchar(‘-‘),x=-x;output(x);putchar(‘ ‘);}
template<class T>il void prt(T a[],int st,int nd){for(reg i=st;i<=nd;++i) ot(a[i]);putchar(‘\n‘);}

namespace Miracle{
const int mod=998244353;
const int G=3;
const int GI=332748118;
const int I=86583718;
const int iv2=499122177;
il int qm(int x,int y){int ret=1;while(y){if(y&1) ret=(ll)ret*x%mod;x=(ll)x*x%mod;y>>=1;}return ret;}
il int ad(int x,int y){return x+y>=mod?x+y-mod:x+y;}
il int sub(int x,int y){return ad(x,mod-y);}
il int mul(int x,int y){return (ll)x*y%mod;}
struct Poly{
    vector<int>f;
    Poly(){f.clear();}
    il int &operator[](const int &x){return f[x];}
    il const int &operator[](const int &x) const {return f[x];}
    il void resize(const int &n){f.resize(n);}
    il int size() const {return f.size();}
    il void cpy(Poly &b){f.resize(b.size());for(reg i=0;i<(int)f.size();++i)f[i]=b[i];}
    il void rev(){reverse(f.begin(),f.end());}
    il void clear(){f.clear();}
    il void read(const int &n){f.resize(n);for(reg i=0;i<n;++i)rd(f[i]);}
    il void out() const {for(reg i=0;i<(int)f.size();++i)ot(f[i]);putchar(‘\n‘);}
}R;
il int init(const int &n){int m;for(m=1;m<n;m<<=1);return m;}
il void rev(Poly &f){
    int lp=f.size();
    if(R.size()!=f.size()) {
        R.resize(f.size());
        for(reg i=0;i<lp;++i){
            R[i]=(R[i>>1]>>1)|((i&1)?lp>>1:0);
        }
    }
    for(reg i=0;i<lp;++i){
        if(i<R[i]) swap(f[i],f[R[i]]);
    }
}
il void NTT(Poly &f,int c){
    int n=f.size();rev(f);
    for(reg p=2;p<=n;p<<=1){
        int gen=(c==1)?qm(G,(mod-1)/p):qm(GI,(mod-1)/p);
        for(reg l=0;l<n;l+=p){
            int buf=1;
            for(reg k=l;k<l+p/2;++k){
                int tmp=mul(f[k+p/2],buf);
                f[k+p/2]=sub(f[k],tmp);
                f[k]=ad(f[k],tmp);
                buf=mul(buf,gen);
            }
        }
    }
    if(c==-1){
        int iv=qm(n,mod-2);for(reg i=0;i<n;++i) f[i]=mul(f[i],iv);
    }
}
il Poly Inv(const Poly &f,int n){
    if(n==1){
        Poly g;g.resize(1);g[0]=qm(f[0],mod-2);return g;
    }
    Poly g=Inv(f,(n+1)>>1),t;
    int m=init(n*2);
    t.resize(m);
    for(reg i=0;i<n;++i)t[i]=f[i];
    g.resize(m);
    NTT(g,1);NTT(t,1);
    for(reg i=0;i<m;++i)g[i]=mul(sub(2,mul(g[i],t[i])),g[i]);
    NTT(g,-1);g.resize(n);
    return g;
}
il void operator *=(Poly &f,Poly g){
    int st=f.size()+g.size()-1;
    int len=init(f.size()+g.size()-1);f.resize(len);g.resize(len);
    NTT(f,1);NTT(g,1);for(reg i=0;i<len;++i) f[i]=mul(f[i],g[i]);
    NTT(f,-1);
    f.resize(st);
}
il void operator *=(Poly &f,const int &c){for(reg i=0;i<f.size();++i) f[i]=mul(f[i],c);}
il Poly operator *(Poly f,const Poly &g){f*=g;return f;}
il Poly operator *(Poly f,const int &c){for(reg i=0;i<f.size();++i) f[i]=mul(f[i],c);return f;}
il void operator +=(Poly &f,const Poly &g){for(reg i=0;i<f.size();++i) f[i]=ad(f[i],g[i]);}
il void operator +=(Poly &f,const int &c){f[0]=ad(f[0],c);}
il Poly operator +(Poly f,const Poly &g){for(reg i=0;i<f.size();++i) f[i]=ad(f[i],g[i]);return f;}
il Poly operator +(Poly f,const int &c){f[0]=ad(f[0],c);return f;}
il void operator -=(Poly &f,const Poly &g){for(reg i=0;i<f.size();++i) f[i]=sub(f[i],g[i]);}
il void operator -=(Poly &f,const int &c){f[0]=sub(f[0],c);}
il Poly operator -(Poly f,const Poly &g){for(reg i=0;i<f.size();++i) f[i]=sub(f[i],g[i]);return f;}
il Poly operator -(Poly f,const int &c){f[0]=sub(f[0],c);return f;}
il Poly operator ~(const Poly &f){return Inv(f,f.size());}
il Poly operator /(Poly f,Poly g){int len=f.size()-g.size()+1;f.rev();g.rev();g.resize(len);f=f*(~g);f.resize(len);f.rev();return f;}
il Poly operator %(Poly f,Poly g){Poly s=f/g;f=f-g*s;f.resize(g.size()-1);return f;}
il Poly Inter(Poly f){int st=f.size();f.resize(st+1);for(reg i=st;i>=1;--i){f[i]=mul(f[i-1],qm(i,mod-2));}f[0]=0;return f;}
il Poly Diff(Poly f){int st=f.size();for(reg i=0;i<st-1;++i) f[i]=mul(f[i+1],(i+1));f.resize(st-1);return f;}
il Poly Ln(const Poly &f){Poly g=Diff(f),h=(~f);g=g*h;g.resize(f.size()-1);return Inter(g);}
il Poly Exp(const Poly &f,int n){
    if(n==1){
        Poly g;g.resize(1);g[0]=1;
        return g;
    }
    Poly g=Exp(f,(n+1)>>1);
    g.resize(n);
    g=g*(((Ln(g)*(mod-1))+1)+f);
    g.resize(n);
    return g;
}
il Poly Exp(const Poly &f){
    return Exp(f,f.size());
}
//i^2=998244352 i=86583718
il Poly Cos(const Poly &f){
    Poly g=Exp(f*I);return (g+(~g))*iv2;
}
il Poly Sin(const Poly &f){
    Poly g=Exp(f*I);return (g-(~g))*qm(ad(I,I),mod-2);
}
int main(){
    int n,t;rd(n);rd(t);
    Poly f;f.read(n);
    if(t==0) (Sin(f)).out();
    else (Cos(f)).out();
    return 0;
}

}
signed main(){
    Miracle::main();
    return 0;
}

/*
   Author: *Miracle*
   Date: 2019/4/8 18:57:00
*/

持(yi)续(ding)更(bu)新(gu)~

原文地址:https://www.cnblogs.com/Miracevin/p/10674814.html

时间: 2024-11-08 16:58:58

多项式全家桶的相关文章

【知识总结】多项式全家桶(一)(NTT、加减乘除和求逆)

我这种数学一窍不通的菜鸡终于开始学多项式全家桶了-- 必须要会的前置技能:FFT(不会?戳我:[知识总结]快速傅里叶变换(FFT)) 一.NTT 跟FFT功能差不多,只是把复数域变成了模域(计算复数系数多项式相乘变成计算在模意义下整数系数多项式相乘).你看FFT里的单位圆是循环的,模一个质数也是循环的嘛qwq.\(n\)次单位根\(w_n\)怎么搞?看这里:[BZOJ3328]PYXFIB(数学)(内含相关证明.只看与原根和单位根相关的内容即可.) 注意裸的NTT要求模数\(p\)存在原根并且\

【知识总结】多项式全家桶(四)(快速幂和开根)

上一篇:[知识总结]多项式全家桶(三)(任意模数NTT) 推荐小恐龙的博客(参考资料):多项式开根 (本文中一切多项式运算默认在模 \(x_n\) 意义下进行) 一.快速幂 多项式快速幂?首先有一种很显然的方式是把整数快速幂里面的整数乘法替换成多项式乘法 NTT ,复杂度 \(O(n\log^2n)\) . 然而还有一种 \(O(n\log n)\) 的做法:要求 \(B=A^k\) ,相当于求 \(\log_A B=k\) ,用换底公式得 \(\log_A B=\frac{\ln B}{\ln

[模板] 多项式全家桶

注意:以下所有说明均以帮助理解模板为目的,不保证正确性. 多项式求逆 已知$A(x)$,求满足$A(x)B(x)=1\ (mod\ x^n)$的B(以下为了方便假设n是2的幂) 考虑倍增,假设已经求出$A(x)B_0(x)=1\ (mod\ x^{n/2})$ $$A(x)(B(x)-B_0(x))=0\ (mod\ x^{n/2})$$ $$(B(x)-B_0(x))=0\ (mod\ x^{n/2})$$ $$(B(x)-B_0(x))^2=0\ (mod\ x^n)$$ $$B^2(x)-

[算法学习] 多项式全家桶

多项式 一个\(n\)次多项式可以表示为\(A(x)=\sum_{i=0}^{n}a_i x^i\),另一个\(n\)次多项式可以表示为\(B(x)=\sum_{i=0}^{n}b_i x^i\). 多项式加法 将\(A(x)\)和\(B(x)\)相加,得到多项式\(C(x)=\sum_{i=0}^{n} (a_i+b_i) x^i\). 复杂度是\(O(n)\)的. 多项式乘法 将\(A(x)\)和\(B(x)\)相乘,得到多项式\(C(x)=\sum_{i=0}^{n}\sum_{j=0}^

[转]vue全面介绍--全家桶、项目实例

慢慢了解vue及其全家桶的过程 原文http://blog.csdn.net/zhenghao35791/article/details/67639415 简介 “简单却不失优雅,小巧而不乏大匠”. 2016年最火的前端框架当属Vue.js了,很多使用过vue的程序员这样评价它,“vue.js兼具angular.js和React.js的优点,并剔除了它们的缺点”.授予了这么高的评价的vue.js,也是开源世界华人的骄傲,因为它的作者是位中国人–尤雨溪(Evan You). Vue.js 是一个J

vue移动端开发全家桶

一句命令搞定全家桶:  npm install vue-router vue-resource vuex --save main.js配置: import Vue from 'vue' import VueResource from 'vue-resource' import VueRouter from 'vue-router' import Vuex from 'vuex' import App from './App.vue' Vue.use(VueResource) Vue.use(Vu

“永恒之蓝”第二弹-Security Update补丁全家桶地址汇总(二)

Security Only Quality Update for Windows 7 for x64-based Systems (KB4012212) 3/14/2017 http://download.windowsupdate.com/d/msdownload/update/software/secu/2017/02/windows6.1-kb4012212-x64_2decefaa02e2058dcd965702509a992d8c4e92b3.msu Security Only Qua

“永恒之蓝”第二弹-Security Update补丁全家桶地址汇总(一)

MS17-010即Windows SMB 服务器安全更新,是微软于2017年3月14日推出的安全更新,此安全更新修复了 Microsoft Windows 中的漏洞. 如果攻击者向 Microsoft 服务器消息块 1.0 (SMBv1) 服务器发送经特殊设计的消息,则其中最严重的漏洞可能允许远程代码执行.有关该漏洞的更多信息,请参阅微软官链:https://technet.microsoft.com/zh-cn/library/security/MS17-010 下列文章包含此安全更新针对具体

vue全家桶(Vue+Vue-router+Vuex+axios)(Vue+webpack项目实战系列之二)

Vue有多优秀搭配全家桶做项目有多好之类的咱就不谈了,直奔主题. 一.Vue 系列一已经用vue-cli搭建了Vue项目,此处就不赘述了. 二.Vue-router Vue的路由,先献上文档(https://router.vuejs.org/zh-cn/). 路由在全家桶里面定位是什么呢,创建单页应用!简单!我们知道Vuejs是一系列的组件组成应用,既然是组件那么就需要组合起来,将组件(components)映射到路由(routes),然后告诉 vue-router 在哪里渲染它们! 我们一般在