FFT是一个很厉害的算法,几乎任何和信号处理有关的算法都依赖于FFT
我们从一个简单的问题中引入FFT:
给定两个多项式,我们希望去计算二者的乘积
中学的时候我们学过,展开相乘就可以了
但是在计算机里面,一个很重要的问题是,如何存储一个多项式?
显然,最自然的方法就是存储多项式的系数,我们把系数映射到一个列表中,这样列表中第k个数字正好对应第k阶系数——>这种表示方法,即是多项式的系数表示法

一般来说,给定两个d阶的多项式,二者的乘积应该是2d阶的多项式,所以如果用naive的乘法分配律来计算,时间复杂度应该是【多项式A中的每一项都会跟多项式B中的所有项分别相乘】
那么问题来了,这个算法可以更快一点吗?
我们知道,任意的d阶多项式,可以由d+1个点唯一确定
即对于一个p阶多项式
p+1个点
确定了之后,多项式的系数可以唯一确定
证明如下:
我们将这d+1个点带入多项式中,得到d+1个方程
将其转化为矩阵&向量的形式
我们可以发现,只要这d+1个x不一样,那么矩阵始终可逆(该矩阵对应的行列式为范德蒙行列式)
于是我们得到了多项式的两种表示方法:
利用值表示法,多项式乘法就变得很简单:
我们知道了乘法之后的阶数为4维,于是我们分别在A(x)和B(x)上取5个点,然后将对应每个点的两个值相乘,得到C在每个点的函数值 。然后根据前面的证明,我们知道,这五个点唯一决定了这个乘积多项式的系数
于是我们不难发现,使用值表示法之后,计算多项式乘法的时间,从原来的
缩短至O(d)
于是我们就可以得到多项式乘法的新框架了:
给定两个d阶多项式,我们已经知道了值表示法计算多项式乘法计算多项式乘法更快,所以我们可以先计算两个多项式在2d+1个点上的值
然后将函数值一对一对乘起来,从而得到乘出来的多项式的值表示
然后,最后一步需要做的是,把值表示转换回系数表示
但问题在于,我们如何把系数形式转换成值表示形式?与此同时,如何把值表示形式转化为系数表示形式?这个就是FFT考虑的内容了
我们先关注从系数表示到值表示的方向
给定d阶多项式和n个点(n≥d+1),我们想计算多项式在这n个点上的值,最简单粗暴的方法就是随便挑选n个点,一个一个地计算函数值
但是这样的问题在于,每一个点的计算都是O(d)的时间复杂度,加起来的时间复杂度还是
——>这样的话,相当于啥都没做
对于奇函数和偶函数,我们可以取一对一对的相反数,这样可以减少一半的采样点
对于一般的函数,我们可以将其分成奇函数+偶函数的形式
然后我们将奇函数的x提出来,得到两个偶函数的形式
我们将两部分都看成
的函数,于是可以发现Pe和Po的阶数都降到了原先的一半
那么,对于
和
,这两个又是两个求值问题
而我们一开始取的是一对一对的相反数,所以这里只剩下一半的点了(n/2)
我们可以看出来,这是一个递归的思想
总结一下就是,我们想计算多项式P在n个点上的值,这n个点是一对一对的相反数
我们将多项式分成两个部分(两个阶为n/2-1的多项式),每个多项式只需要求n/2个点的值
我们只需要递归地求解这两个分多项式的值,就可以得到原多项式的n个值
如果这一切可行,那么我们的时间复杂度是O(nlogn)【每一层对应点的值相乘还是n,只不过现在从上到下,每一层阶数减半,故只有logn层】
但是至此为止,还是有一个小问题,就是从第一次迭代开始,和
只能取正值,但我们希望新的求指点也可以是相反数
于是我们在这里引入了复数的概念

1的n次方根,用图像表示,可以解释为在复平面上沿着单位元等距排布的一系列点,其中任意两点之间的夹角为

用欧拉公式,可以很简单地表达这些点:

所以我们找的值就是1,ω,...

与此同时,我们知道,于是再做修改

同时,我们又有

于是进一步,可以写成


已知一个序列 ,我们可以用
个傅里叶系数表示,其中第k项为

实际上差值和求值是紧密联系的,我们之间将求值问题表示为矩阵-向量 乘积


因为FFT中的x是1的n次方根,所以可以改写为

这个矩阵被称为离散傅里叶变换矩阵DFT
而我们的差值,即取逆即可


参考资料:The Fast Fourier Transform (FFT): Most Ingenious Algorithm Ever? - YouTube
目录前言滤波电路科普主要分类实际情况单位的概念常用评价参数函数型滤波器简单分析滤波电路构成低通滤波器RC低通滤波器RL低通滤波器高通滤波器RC高通滤波器RL高通滤波器部分摘自《LC滤波器设计与制作》,侵权删。前言最近需要学习放大电路和滤波电路,但是由于只在之前做音乐频谱分析仪的时候简单了解过一点点运放,所以也是相当从零开始学习了。滤波电路科普主要分类滤波器:主要是从不同频率的成分中提取出特定频率的信号。有源滤波器:由RC元件与运算放大器组成的滤波器。可滤除某一次或多次谐波,最普通易于采用的无源滤波器结构是将电感与电容串联,可对主要次谐波(3、5、7)构成低阻抗旁路。无源滤波器:无源滤波器,又称
有没有办法快速将表格格式的ruby哈希打印到文件中?如:keyAkeyBkeyC...1232343451253474456...其中散列的值是不同大小的数组。还是使用双循环是唯一的方法?谢谢 最佳答案 试试我写的这个gem(在表中打印散列、ruby对象、ActiveRecord对象):http://github.com/arches/table_print 关于ruby-如何以表格格式快速打印Ruby哈希值?,我们在StackOverflow上找到一个类似的问题:
ruby中有这样的东西吗?send(+,1,2)我想让这段代码看起来不那么冗余ifop=="+"returnarg1+arg2elsifop=="-"returnarg1-arg2elsifop=="*"returnarg1*arg2elsifop=="/"returnarg1/arg2 最佳答案 是的,只需像这样使用send(或者更好的是public_send):arg1.public_send(op,arg2)这是可行的,因为Ruby中的大多数运算符(包括+、-、*、/、andmore)只需调用方法。所以1+2与1.+(2)相同
电脑启动出现显示器黑屏是一个相当常见的问题。如果您遇到了这个问题,不要惊慌,因为它有很多可能的原因,可以采取一些简单的措施来解决它。在本文中,小编将介绍下面4种常见的电脑启动后显示器黑屏的原因,排查这些原因,快速解决! 演示机型:联想Ideapad700-15ISK-ISE系统版本:Windows10一、显示器问题如果出现电脑启动后显示器黑屏的情况。那么首先您需要检查一下显示器是否正常工作。您可以通过更换另一个显示器或将当前显示器连接到另一台计算机来检查显示器是否存在问题。如果问题仍然存在,那么您可以排除显示器故障的可能性。 二、显卡问题如果您的电脑配备了独立显卡,那么显卡故障也可能是导致电脑
写在之前Shader变体、Shader属性定义技巧、自定义材质面板,这三个知识点任何一个单拿出来都是一套知识体系,不能一概而论,本文章目的在于将学习和实际工作中遇见的问题进行总结,类似于网络笔记之用,方便后续回顾查看,如有以偏概全、不祥不尽之处,还望海涵。1、Shader变体先看一段代码......Properties{ [KeywordEnum(on,off)]USL_USE_COL("IsUseColorMixTex?",int)=0 [Toggle(IS_RED_ON)]_IsRed("IsRed?",int)=0}......//中间省略,后续会有完整代码 #pragmamulti_c
TCL脚本语言简介•TCL(ToolCommandLanguage)是一种解释执行的脚本语言(ScriptingLanguage),它提供了通用的编程能力:支持变量、过程和控制结构;同时TCL还拥有一个功能强大的固有的核心命令集。TCL经常被用于快速原型开发,脚本编程,GUI和测试等方面。•实际上包含了两个部分:一个语言和一个库。首先,Tcl是一种简单的脚本语言,主要使用于发布命令给一些互交程序如文本编辑器、调试器和shell。由于TCL的解释器是用C\C++语言的过程库实现的,因此在某种意义上我们又可以把TCL看作C库,这个库中有丰富的用于扩展TCL命令的C\C++过程和函数,所以,Tcl是
情况:我正在编写一个程序来求解素数。我需要解决4x^2+y^2=n的问题,其中n是一个已知变量。是的,必须是Ruby。我愿意在这个项目上花费大量时间。我最好自己编写方程式的求解算法,并将其作为该项目的一部分。我真正喜欢的是:如果任何人都可以向我提供指南、网站的链接,或者关于与求解代数方程特别相关的形式算法的构造的歧义消除,或者向我提供似乎你是读者它会帮助我完成任务。请不要建议我使用其他语言。如果您在回答之前接受我真的非常想这样做,我将不胜感激。该项目没有范围或时间限制,也不以营利为目的。这是为了我自己的教育。注意:我并不直接反对为Ruby实现和使用现存的数学库/模块/其他东西,但我更喜
mutationtesting遇到一个问题是它很慢,因为默认情况下您会为每个生成的突变执行完整的测试运行(测试文件或一组测试文件)。加快突变测试的一种方法是,一旦遇到单一故障(但仅在突变测试期间),就停止对给定突变体的测试运行。更好的做法是让变异测试者记住杀死最后一个变异体的第一个测试是什么,并将其首先交给下一个变异体。ruby中是否有任何东西可以做这些事情,或者我最好的选择是开始猴子修补?(是的,我知道单元测试应该很快。显示所有失败的测试在突变测试之外很有用,因为它不仅可以帮助您识别出问题,还可以查明哪里出了问题)编辑:我目前正在对测试/单元使用heckle。如果测试/单元不可能记住
我发现许多Rails应用程序主要针对企业、社交网络类型的Web应用程序。我看到有人将Ruby与一些出色的OOPS语言(如Java和C#)进行了比较,但我确实发现很难获得一些数学密集型应用程序。非常感谢任何知识渊博的输入(指向示例程序的链接等),其中轻松显示了语言的用法,就像快速启动或显示该语言如何用于各种数学问题一样。 最佳答案 不幸的是,Ruby并没有在数学和科学计算领域涉足太多。目前,有一个名为SciRuby的pre-alpha库它试图为Ruby带来更多面向数学的功能。他们正试图构建一个NumPy/SciPy等价物。SciRub
我有两个类:1.Sale是ActiveRecord的子类;它的工作是将销售数据持久保存到数据库中。classSale2.SalesReport是一个标准的Ruby类;它的工作是生成和绘制有关销售的信息。classSalesReportdefinitialize(start_date,end_date)@start_date=start_date@end_date=end_dateenddefsales_in_durationSale.total_for_duration(@start_date,@end_date)end#...end因为我想使用TDD并且我希望我的测试运行得非常快,所