SSL 1383 车Ⅱ 状压dp
来源:互联网 发布:淘宝主图1920显示不全 编辑:程序博客网 时间:2024/05/20 00:11
有一个n*m的棋盘(n、m≤80,n*m≤80)要在棋盘上放k(k≤20)个棋子,使得任意两个棋子不相邻。求合法的方案总数。
我们用数组s保存一行中所有的num个放置方案,则s数组可以在预处理过程中用DFS求出,同时用ci保存第i个状态中1的个数以避免重复计算。开始设计状态。本题状态的维数需要增加,原因在于并不是每一行只放一个棋子,也不是每一行都要求有棋子,原先的表示方法已经无法完整表达一个状态。我们用fi,j,k表示第i行的状态为sj且前i行总共放置k个棋子(下面用pn代替原题中的k)的方案数。沿用枚举当前行方案的做法,只要当前行的放置方案和上一行的不冲突。微观地讲,就是要两行的状态s1和s2中没有同为1的位即可,亦即s1&s2=0。然而,虽然我们枚举了第i行的放置方案,但却不知道其上一行(第i-1行)的方案。为了解决这个问题,我们不得不连第i-1行的状态一起枚举
<pre name="code" class="plain">var d:array[1..10] of longint; a,b:array[1..100] of longint; f:array[0..80,0..1000,0..10] of longint; ans,n,m,p,i,j,k,l,a1:longint;procedure dfs(x:longint);var i:longint;begin if x>m then begin inc(a1); for i:=1 to m do begin a[a1]:=a[a1]+(1 shl (i-1))*d[i]; inc(b[a1],d[i]); end; exit; end; dfs(x+1); d[x]:=1; dfs(x+2); d[x]:=0;end;begin readln(n,m,p); if n<m then begin n:=n xor m; m:=n xor m; n:=n xor m; end; dfs(1); f[0,0,0]:=1; for i:=1 to n do for j:=0 to p do for k:=1 to a1 do if j>=b[k] then for l:=1 to a1 do if a[k] and a[l]=0 then f[i,a[k],j]:=f[i,a[k],j]+f[i-1,a[l],j-b[k]]; for i:=1 to a1 do ans:=ans+f[n,a[i],p]; writeln(ans);end.
0 0
- SSL 1383 车Ⅱ 状压dp
- SSL 1382 车 状压dp
- SSL 1507 棋盘 状压dp
- SSL 1317 海上搜索 状压dp
- SSL 1565 将功补过 树形dp
- SSL 1033 加分二叉树 dp
- SSL 1605 二叉苹果树 树形dp
- SSL 1230 战略游戏 树形dp
- SSL 1608 皇宫看守 树形dp
- 平衡二叉树 ssl 2633 dp
- SSL 1606 选课 树转二叉树+树形dp
- SSL 1607 没有上司的晚会 树形dp
- SSL
- SSL
- ssl
- SSL
- ssl
- ssl
- 【ZOJ3229】Shoot the Bullet 有源汇上下界最大流
- VB.net中获取二维数组的元素个数
- AppBarLayout的使用
- windows下配置Mysql-5.7.9服务
- [bzoj3531][SDOI2014]旅行
- SSL 1383 车Ⅱ 状压dp
- C/C++的内存处理函数
- 06.3.4工作笔记
- App Transport Security has blocked a cleartext HTTP (http://) resource load since it is insecure. Te
- 寒假刷题-最小生成树
- hdu4605 树状数组+离散化+dfs
- 显式调用构造函数
- 程序员每天自我洗脑和催眠
- C# 线程池中取消线程的三种方式