网页
资讯
视频
图片
知道
文库
贴吧
地图
采购
进入贴吧
全吧搜索
吧内搜索
搜贴
搜人
进吧
搜标签
日
一
二
三
四
五
六
签到排名:今日本吧第
个签到,
本吧因你更精彩,明天继续来努力!
本吧签到人数:0
一键签到
成为超级会员,使用一键签到
一键签到
本月漏签
0
次!
0
成为超级会员,赠送8张补签卡
如何使用?
点击日历上漏签日期,即可进行
补签
。
连续签到:
天 累计签到:
天
0
超级会员单次开通12个月以上,赠送连续签到卡3张
使用连续签到卡
04月13日
漏签
0
天
c语言吧
关注:
799,016
贴子:
4,353,687
看贴
图片
吧主推荐
视频
游戏
24
回复贴,共
1
页
<<返回c语言吧
>0< 加载中...
大一懵逼系列
只看楼主
收藏
回复
皓平川海
大能力者
8
该楼层疑似违规已被系统折叠
隐藏此楼
查看此楼
这道题的算法标签是“状压DP”,我第一次见
我想能不能搜索+剪枝做出来,但是我只得到了50
请问还有什么优化方案吗
求大佬指点一下
Lason•᷄ࡇ•᷅
彩虹面包
13
该楼层疑似违规已被系统折叠
隐藏此楼
查看此楼
小优化,re不需要是map,可以是unordered_map或者int数组之类。map底层实现是红黑树,查找时间复杂度并非常数。
不过,既然是dp题,为什么要用暴搜折磨自己呢
皓平川海
大能力者
8
该楼层疑似违规已被系统折叠
隐藏此楼
查看此楼
70分代码,还能继续优化吗
逢部祝
强能力者
7
该楼层疑似违规已被系统折叠
隐藏此楼
查看此楼
楼主把记忆化加上,DFS就不会超时了
但无论怎么说,还是用一个二进制mask表示有哪些口味的糖果才是正解,M不超过20的数据规模几乎是在求着你用二进制了
asher
毛蛋
1
该楼层疑似违规已被系统折叠
隐藏此楼
查看此楼
楼主可以试试状压加bfs 把每个品种转为位掩码看作是一个节点,全部入队,跑一边bfs就行了 状压dp感觉时间挺极限的
星之天仪
超能力者
9
该楼层疑似违规已被系统折叠
隐藏此楼
查看此楼
虽然写的是递归,但我测试过了,洛谷P8687,能全部Accept
星之天仪
超能力者
9
该楼层疑似违规已被系统折叠
隐藏此楼
查看此楼
简述一下思路
1. 因为糖果的口味数不超过20,所以用一个uint32_t来表示状态,这也是所谓状压DP中的状压,即状态压缩,对于每一包糖果,如果它包含口味i,则第i-1位置为1(口味从1-N,对应的位从0到N-1),代码中的final_state为0到N-1位全置为1,也就是要覆盖所有口味的意思。糖果包的信息存储于candy_info[100]中
2. DP,方程为 F(i, j) = min(F(i-1,Q) + 1, F(i-1, j))
其中F(i, j)表示,使用所有标号不超过i的糖果包(这里一共有i+1包),要达到状态j,至少需要几包
这里Q是一个集合相减结果状态,就是j状态对应所有的口味,对candy_info[i]对应的所有口味做一个集合减法(留下属于前者但不属于后者的元素),以状态位来表示如下
Q = j & (~candy_info[i])
这个状态转移的理解方式是,如果F(i,j)达到最少包数时,不使用第i包,那么它就相当于F(i-1, j),如果使用第i包,那该使用方法的其他糖果包一定能覆盖Q,再加上1包(第i包)则能覆盖j
3. 考虑到如果Q = j,则min值一定为后者,不必进行2项展开。因为根据题目数据范围,j最多为20位,所以如果Q != j,则Q至少要比j少1为,所以进行两项展开的层数不会超过20层。
4, i == 0和j == 0均为递归终止条件,其中j = 0表示不需要覆盖任何口味,所以0包即可完成, i = 0表示只用第0包糖果能否覆盖状态j,可以简单计算。
5. 以递归形式实现,为了防止重复计算,使用一个大数组dp[][]存储计算过的结果,i不超过100,j不超过2^20,因为F(i, j)的值不超过20,所以可以用unsigned char存储。计算F(i, j)时先查表,如果找不到再计算,算完存表。
登录百度账号
扫二维码下载贴吧客户端
下载贴吧APP
看高清直播、视频!
贴吧页面意见反馈
违规贴吧举报反馈通道
贴吧违规信息处理公示