0
点赞
收藏
分享

微信扫一扫

状态压缩习题

王栩的文字 2022-02-19 阅读 54
c++

文章目录

P2704 [NOI2001] 炮兵阵地

题目链接
参考题解
因为列数仅为10,考虑使用状态压缩,用一个数字 s s s表示某行的炮兵放置情况,当 s s s二进制的 k k k位为1,该行的 k k k列就放置了炮兵。
预处理: 因为要计算炮兵的数量,先计算每个状态 s s s的炮兵个数(即二进制中 1 1 1的数量) s u m [ s ] sum[s] sum[s]

状态设计: d p [ i ] [ s 1 ] [ s 2 ] dp[i][s1][s2] dp[i][s1][s2]表示前 i i i行已经安排好,第 i − 1 i-1 i1行的状态为 s 1 s1 s1,第 i i i行的状态为 s 1 s1 s1,可以放置的最多炮兵数量。起始状态是第一行所有合法状态。
状态转移: 其实状态转移比较简单,比较冗杂的是状态转移的判断。分三种情况:避免当前行的炮兵放置在山地上;避免当前行的炮兵相互攻击;如果有上一行(上上行),需要避免当前行和上一行(上上行)的炮兵相互攻击。如果都合法就增加当前行安排的状态的炮兵数量。

空间优化: 需要安排好前 i − 1 i-1 i1行才能开始安排第 i i i行,也就是说第 i i i行的状态只和前 i − 1 i-1 i1行有关,因此保存第前一行和当前行的状态就够了。

举报

相关推荐

0 条评论