作用
给定一个n次多项式f的n+1个点值,在O(n*n)的时间复杂度内求出f(x)的值。
(一般应先对式子进行推导,展开,确定其为以什么为自变量的多项式)
经典应用如求
这就是一个以n为底的k+2次多项式。例题:https://www.luogu.org/problemnew/show/CF622F
#include<cstdio> #include<iostream> #include<ctype.h> using namespace std; #define ll long long inline ll rd() { ll x=0,f=1;char c=getchar(); while(!isdigit(c)){if(c=='-')f=-f;c=getchar();} while(isdigit(c)){x=(x<<1)+(x<<3)+(c^48);c=getchar();} return x*f; } const int N=1e6+13,P=1e9+7; ll fac[N],y[N]; ll ksm(ll x,ll n){ll ans=1;for(;n;n>>=1,x=x*x%P)if(n&1)ans=ans*x%P;return ans;} int main() { int n=rd(),k=rd();fac[0]=1;ll g=n,ans=0,a,b; for(int i=1;i<=k+1;i++) fac[i]=fac[i-1]*i%P,g=g*(n-i)%P; for(int i=1;i<=k+1;i++) y[i]=y[i-1]+ksm(i,k),y[i]=y[i]<P?y[i]:y[i]-P; if(n<=k+1){printf("%lld",y[n]);return 0;} for(int i=0;i<=k+1;i++) { b=fac[i]*fac[k+1-i]%P*(n-i)%P;if((k+1-i)&1)b=P-b; b=ksm(b,P-2)*y[i]%P,ans+=b,ans=ans<P?ans:ans-P; } printf("%lld",ans*g%P); }
公式
模板
P4781 【模板】拉格朗日插值 - 洛谷 | 计算机科学教育新生态
https://www.luogu.org/problemnew/show/P4781
#include<cstdio> #include<iostream> #include<ctype.h> #include<cmath> using namespace std; #define ll long long inline ll rd() { ll x=0,f=1;char c=getchar(); while(!isdigit(c)){if(c=='-') f=-f;c=getchar();} while(isdigit(c)){x=(x<<1)+(x<<3)+(c^48);c=getchar();} return x*f; } const int P=998244353; int a[2003],b[2003]; ll KSM(ll x,int n) { ll ans=1; while(n){if(n&1) (ans*=x)%=P;(x*=x)%=P;n>>=1;} return ans; } ll ans=0; int main() { int n=rd(),K=rd(); for(int i=1;i<=n;i++) a[i]=rd(),b[i]=rd(); for(int i=1;i<=n;i++) { ll p=1,q=1; for(int j=1;j<=n;j++) if(i!=j) (q*=(K-a[j]))%=P,(p*=(a[i]-a[j]))%=P; (ans+=q*KSM(p,P-2)%P*b[i]%P)%=P; } if(ans<0) ans+=P; printf("%lld",ans); return 0; }