FFT学习笔记

news/2024/9/2 1:48:48 标签: c++

1.什么事FFT?(恼

百度百科传送门

2.为什么要用FFT?

  • 在计算两个多项式相乘的时候,我们要将两个多项式的项数一一对应相乘。

  • 所以计算 f ( x ) ∗ g ( x ) f(x)*g(x) f(x)g(x) 时,时间复杂度为 O ( n 2 ) O(n^2) O(n2)

  • 但是我们可以将函数用另一种表示方法。

  • 总所周知,用 n + 1 n+1 n+1 个点可以确定一个 n n n 次的函数(传送门),所以我们不妨写成(以 f ( x ) f(x) f(x)为例)

    f ( x ) = { ( x 0 , f ( x 0 ) ) , ( x 1 , f ( x 1 ) ) , . . . , ( x n , f ( x n ) ) } f(x)= \{(x0,f(x0)),(x1,f(x1)),...,(xn,f(xn))\} f(x)={(x0,f(x0)),(x1,f(x1)),...,(xn,f(xn))}

    即用坐标表示一个多项式函数。

  • 但有什么用呢?

    假设我们要求 f ( x ) ∗ g ( x ) f(x)*g(x) f(x)g(x)(设 f ( x ) , g ( x ) f(x),g(x) f(x)g(x) 的次数为 n n n)的结果(自然也是一个多项式,设为 h ( x ) h(x) h(x) 罢)

    若我们用坐标来求解,那么

    h ( x ) = { ( x 0 , f ( x 0 ) ∗ g ( x 0 ) ) , ( x 1 , f ( x 1 ) ∗ g ( x 1 ) ) , . . . , ( x n , f ( x n ) ∗ g ( x n ) ) } h(x)= \{ (x0,f(x0)*g(x0)),(x1,f(x1)*g(x1)),...,(xn,f(xn)*g(xn))\} h(x)={(x0,f(x0)g(x0)),(x1,f(x1)g(x1)),...,(xn,f(xn)g(xn))}

    O ( n ) O(n) O(n) 的。

  • 但是很可惜,多项式表示变换为坐标的时间复杂度事 O ( n 2 ) O(n^2) O(n2) 的(恼

    因为你不仅要枚举 n + 1 n+1 n+1 个不同的 x x x ,还要将每一个 x x x 带入。

    所以这时候就要用到 F F T FFT FFT

3.FFT代码

已经有人讲的很详细了,再详细也没有用了罢(悲

所以不再赘述了,链接直接贴出来(这事会员制博客,作者受到的惩罚是。。。(悲):

LeeCongWei
【学习笔记】极其美妙的算法——FFT(快速傅里叶变换)

路人黑的纸巾
十分简明易懂的FFT(快速傅里叶变换)

lahlah_
浅谈 FFT (终于懂一点了~~)

#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
#include<cmath>
#include<complex>
#define co complex<double>
#define pi acos(-1.0)
using namespace std;
int n,m;
long long limt=1;
co a[4000200],b[4000200];
int rev[4000200];
void fft(co *c,int inv)
{
	for(int i=0;i<limt;i++)
	if(i<rev[i]) swap(c[rev[i]],c[i]);
	for(int mid=1;mid<limt;mid<<=1)
	{
		int len=mid*2;
		co w(cos(pi/mid),inv*sin(pi/mid));
		for(int i=0;i<limt;i+=len)
		{
			co omega(1,0);
			for(int j=0;j<mid;j++)
			{
				co p1=c[i+j],p2=omega*c[i+j+mid];
				c[i+j]=p1+p2;
				c[i+j+mid]=p1-p2;
				omega=w*omega;
			}		
		}
	}
}
int main()
{
	scanf("%d %d",&n,&m);
	for(int i=0;i<=n;i++)
	cin>>a[i];
	for(int i=0;i<=m;i++)
	cin>>b[i];
	while(limt<n+m+1)
	limt*=2;
	for(int i=0;i<limt;i++)
	if(i&1)
	rev[i]=((rev[i>>1]>>1)+limt/2);
	else
	rev[i]=(rev[i>>1]>>1);
	fft(a,1),fft(b,1);
	for(int i=0;i<limt;i++)
	a[i]*=b[i];
	fft(a,-1);
	for(int i=0;i<=n+m;i++)
	printf("%d ",(int)(a[i].real()/limt+0.5));
}

作者只是个背板子的食雪汉(悲


http://www.niftyadmin.cn/n/1318750.html

相关文章

Weblogic10两种修改端口的方法

一.进入控制台进行修改 1.进入控制台: http://127.0.0.1:7001/console 2.展开左边树菜单 域结构->环境->服务器-->点击AdminServer(管理) 3.修改监听端口 4.点击保存按钮 二.修改配置文件 打开$WEBLOGIC_HOME/user_projects/domains/base_do…

树上莫队学习笔记

众所周知&#xff0c;莫队算法不仅仅能解决序列问题&#xff0c;还能解决树上问题。 当一个问题可以离线做时&#xff0c;我们就可以使用树上莫队算法了&#xff08;带修另说&#xff09; 基本思路 一道例题&#xff1a;给一棵树&#xff0c;树上节点都有颜色 col[i]col[i]co…

概率期望学习笔记

概率 定义 Ω\OmegaΩ &#xff1a;样本空间&#xff0c;随机实验得到的所有样本。 A1...nA_{1...n}A1...n​ &#xff1a;发生的事件&#xff08;即为 Ω\OmegaΩ 的子集&#xff09;。 P(A)P(A)P(A)&#xff1a;事件 AAA 发生的概率。 P(AB)P(AB)P(AB)&#xff1a; 事件 AAA…

解决 entity framework 操作非自增主键时报错Field doesn't have a default value

前一篇提到EF在对具有非自增的主键表进行插入时出现 Field merchant_id doesnt have a default value 错误。&#xff08;地址&#xff1a;http://www.cnblogs.com/tangfd405/p/3155893.html&#xff09; 解决方法&#xff1a; 在EF实体对应的字段上标注DatabaseGenerated(Dat…

easyTemplate概述与实例

一.概述 在前后端分离的解决方案中&#xff0c;模板起到了重要作用&#xff01; 在使用Struts或Spring的后端中&#xff0c;使用Freemarker模板作为载体&#xff0c;能够非常有效的实现前后端的分离。  有人或许会认为使用前端模板一样可以实现此效果&#xff0c;而且实现的会…

概率论好题:洛谷P5389 [Cnoi2019]数学课

题目大意 给定一个序列 aaa &#xff0c;满足 an123...na_{n}123...nan​123...n&#xff0c;根据题目给定的概率选择其中两个&#xff08;可相同&#xff09;的元素 v1,v2v1,v2v1,v2 &#xff0c;我们记录 a∈[1...v1]a \in [1...v1]a∈[1...v1]&#xff0c;b∈[1...v2]b \in…

easyTemplate实例

实例一&#xff1a;list简单应用 <!doctype html> <html><head><script src"lib/jquery-1.7.2.js" type"text/javascript"></script><script src"lib/easy.template.js" type"text/javascript">&…

vs2010 打开 vs2012/vs2013 的解决方案

vs2012 出来了&#xff0c;但是MS还是一如既往的向上兼容。 废话不多说&#xff0c;直接主题 PS:vs2013 的文件标准和12的类似&#xff0c;所以转换规则都差不多。 要使用vs2010打开vs2012的解决方案必须得改2个东西&#xff0c;解决方案 和 工程文件 解决方案就是后缀名为 .sl…