高维前缀和

高维前缀和

Tags:动态规划

作业部落

评论地址


一、概述

高维前缀和是个好东西,很多人把它归类为状态压缩\(DP\),其实听说它是由\(FWT\)衍生出来的黑科技?

求x二进制下的超集或子集的所有状态之和怎么办?
(如\(0101\)超集为\(0101,1101,0111,1111\),子集为\(0101,0001,0100,0000\)
高维前缀和可以把这个过程从\(2^n×2^n\)优化到\(n×2^n\)(\(2^n\)为最大值域范围)

二、原理

通过高维前缀和的枚举顺序,可以保证枚举到第\(i\)位的\(1\),所有第\(i+1\)到末位的数的超集(子集)情况都被涵盖在内,具体原理理解请照代码手玩\(0-7\)(博主就是靠这个理解的,但是太懒不想做表了,毕竟还有辣么多东西还没学还没总结)

枚举超集

for(int j=0;j<n;j++)
    for(int i=0;i<1<<n;i++)
        if(!(i&(1<<j))) f[i]+=f[i|(1<<j)];

枚举子集

for(int j=0;j<n;j++)
    for(int i=0;i<1<<n;i++)
        if(i&(1<<j)) f[i]+=f[i^(1<<j)];

这里可以自定义运算,可以取最值等等
\(Update7.21\):其实求子集就是\(FWT\_or(f,1)\),求超集就是\(FWT\_and(f,1)\),不过高维前缀和可以资瓷不只是乘法的更多操作

三、做题经验

1.巧用容斥

很多情况需要求的是恰好怎样的答案,这个时候可以改为至少怎样的方案,然后用\(\pm1\)容斥或者组合数容斥解决
\(eg:\)考试2018.7.9T1、[CF449D]Jzzhu and Numbers

2.巧妙转化子集超集

可以考虑\(01\)翻转后计算贡献
\(eg:\)[SPOJ2829]Time Limit Exceeded

附录:题单

转载于:https://www.cnblogs.com/xzyxzy/p/9325435.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值