Preface
我们知道,对于下面的式子
当为+运算时,可以用FFT优化
当为位运算(or,and,xor)时是否也有一种优化呢
答案是肯定的。
FWT
首先,对于多项式,我们定义为某一种位运算卷积
显然它满足交换律、结合律
类似FFT。我们利用分治的思想,将多项式分成两部分和,表示其下标二进制最高位为0的部分(前项)和最高位为1的部分(后项),不足的不妨用0补齐
那么A是由两部分拼接而成,记为
对于一个多项式A,我们尝试找到一种变换
满足:
并且它存在逆变换,满足
这样对于两个多项式位运算卷积我们就可以先将它们变换,直接按项相乘,再变换回来
下面结论就来了
or卷积
当为or运算时
当然只有一个数时就是它本身
实际上,
and卷积
当为and运算时
xor 卷积
当为xor运算时
并且对于所有的变换,都满足
证明可以用数学归纳法,拆成两部分推导一波…博主太懒不想推了
接下来就可以快乐写FWT了
过程和FFT是类似的,不过不需要蝴蝶变换的反位
Code
or
And
Xor
一个应用(子集卷积)
有时候我们常常要碰到这样的问题
也就是子集卷补集
这似乎不太好处理
巧妙的转化一下
,其中为i在二进制下1的个数
如果我们将所有数按bit分组,每一组存一个多项式,只有bit数对应的项才有值,其他项为0
这就变成
相当于里面的位运算卷积外面套一个普通的卷积。
枚举,再枚举i,和可以提前预处理好,这里直接相乘
又由于。
因此我们可以直接累加进,最后全部做完了再一次性回来
注意不同的bit[n]之间的F是不能加在一起的,一个bit[n]做完以后只有bit对应的项的值是有意义的。
这样预处理和后面乘积累加时间复杂度都是,空间复杂度