`
yuanlanxiaup
  • 浏览: 896248 次
文章分类
社区版块
存档分类
最新评论

POJ 2411 大矩形用1X2小矩形填充 状态dp DFS

 
阅读更多

这题和编程之美上面的“地板覆盖”问题有点像,不同的是,编程之美上面只需要判定能否覆盖,这题需要求出总方案数目

结题报告转自http://duanple.blog.163.com/blog/static/709717672008930104124684/

题意:给你一个h*w的矩形,用一个1*2的小矩形去填充,问有多少种填充方法,不考虑对称性。

关键点提示:

1.DFS部分

实际上是在枚举第i行的放置方法,由此便可以确定出该行及上一行的状态。

对于第i行,状态(参数next_stat)的定义是指,前i-1行完全放满,第i行的所有位置是否放置(0,1表示)组成的二进制序列,转化为十进制数后所代表的状态。

放置方法,总共存在三种,
1. 竖直放置
2. 水平放置
3. 不放置

以竖直放置举例说明:

假设第i行的第3列位置是要竖直放置,则说明它的前一行该列位置必然是0,放置后这一行的状态必然变成了1,所以上一行的状态应该是prev_stat << 1,该行是(next_stat << 1)|1,直到column == w,即从左到右开始枚举,枚举到了最右列,说明该放置方案完毕。

本质上是枚举的第i行的放置方案,而放置方案实际上确定了上下两行的状态。

2.注意到prev_stat并没有明确指明列值,对于列的变化实际上是通过移位来反映的。

prev_stat,next_stat初始均为0,第一次移位确定的是左边第一个位置的状态,这样随着移位的进行这个状态不断的往高位迁移,这样在以后的移位,或运算中保证保持不变。也就是说,随着移位的进行,本来第一位表示的是最左边那列的状态,慢慢得变成第2,3,4,...w位来表示它的状态,实际上是该状态值不断得伴随着移位再向高位迁移。

DFS+DP解法解题报告

当高度和宽度都为奇数时显然答案为0, 这个用面积的奇偶性就很容易得证
记f[i][s1]为第i-1行全满且第i行状态为s1时的种数,便有如下递推关系:
f[i][s1] = sigma(f[i-1][s2]);
其中(s1, s2)整体作为一个放置方案, 这样f[h+1][0]即是答案了

对于每一个位置,我们有三种放置方法:
1. 竖直放置
2. 水平放置
3. 不放置

d为当前列号 ,初始化d, s1, s2都为0;对应以上三种放置方法,s1, s2的调整为:

1. d = d + 1, s1 << 1 | 1, s2 << 1;
2. d = d + 2, s1 << 2 | 3, s2 << 2 | 3;
3. d = d + 1, s1 << 1, s2 << 1 | 1;

先就第一种情况解释一下,另外的两种情况可以类推

S1<<1|1即为把s1的二进制表示后面加上一个1,对就于本题来说就是(d+1)列上放
置,s2<<1即为把s2的二进制表示后面加上一个0,对于本题来说就是(d+1)列上不放置。

但为什么s1、s2会如此变化呢?本人在此处想了好长时间,后来想明白了,s1对应于本行的状态,s2对应

于上一行的状态,能竖直放置意味着上一行的(d+1)列是空着的,因此此时上一行的状态为s2<<1,同时竖

置放置了之后,则本行(d+1)行放置了东西,状态于是变为s1<<1|1;
当d = w时保存状态

对于初始时的f值,可以假设第0行全满,第一行只有两种放法:

1. 水平放置 d = d + 2, s << 2 | 3;
2. 不放置 d = d + 1, s << 1;
另外,利用滚动数组,可以减少空间的开销
还有一个可以提高较率的地方,当输入的 w > h 时,对调,因为横向的运算是指数
级的, 而列向的是线性的.




分享到:
评论

相关推荐

    POJ 2411 Mondriaan's Dream详细解题报告

    - **状态定义**:设`dp[i][j]`表示高度为i、宽度为j的大矩形可以被2x1的小矩形填充的方法数。 - **边界条件**:对于宽度为1的情况,若高度为奇数,则无法完全填充;若高度为偶数,则只有1种填充方式。 - **递推公式*...

    poj dp总结,动态规划分类

    ### poj dp总结:动态规划分类 #### 概述 动态规划(Dynamic Programming,简称DP)是一种在计算机科学和数学中广泛使用的算法策略,用于解决最优化问题。它通过将复杂问题分解为较简单的子问题来求解,并利用这些...

    poj 1191 经典dp 源代码

    - `init()` 函数用于初始化 dp 数组,并计算当 n=1 时的所有可能状态。 #### 2. 主要逻辑 ```cpp double solve(int n, int lx, int ly, int rx, int ry) { // 基本情况:n == 1 if (n == 1) return dp[1][lx][ly...

    poj 3342(树状dp)

    ### Poj 3342 (树状DP) #### 题目背景 这是一道典型的树状动态规划问题,来源于POJ平台编号为3342的题目。题目描述了一个公司的组织结构,并提出了一种特定场景下的最优解求法。 #### 题目解析 在题目描述中提到...

    POJ-2870 Light Up + DFS(1级DFS+1级DFS) + Python - 思维导图

    题目"POJ-2870 Light Up"是一个经典的图论问题,主要涉及深度优先搜索(DFS)算法的运用。该问题要求点亮一个矩形区域内的所有障碍物,每个障碍物需要特定数量的灯光才能被照亮,且相邻的障碍物之间不能有空格。题目...

    POJ3373-Changing Digits【DFS+强剪枝】

    标题“POJ3373-Changing Digits【DFS+强剪枝】”涉及的是一个编程竞赛中的问题,这个问题在北大POJ(北京大学在线评测系统)平台上被提出。"Changing Digits"是一个算法挑战,而解决方案是通过深度优先搜索(DFS)...

    POJ1020-Anniversary Cake【有技巧的DFS】

    【标题】"POJ1020-Anniversary Cake【有技巧的DFS】"是一个源自北京大学在线编程平台POJ的编程题目,它涉及到深度优先搜索(DFS)算法的应用。这道题目要求参赛者通过编程解决一个有趣的问题,即在特定条件下如何...

    POJ1014-Dividing【DFS】【多重背包+二进制优化】

    标题中的“POJ1014-Dividing”是指北京大学在线编程平台POJ(Problemset Online Judge)上的一个问题编号为1014的题目。这个题目通常会涉及到计算机科学和算法设计,特别是优化问题的解决方案。这里的关键词是“DFS...

    POJ3733-Changing Digits【DFS+强剪枝】

    【标题】"POJ3733-Changing Digits【DFS+强剪枝】"是一个来自北京大学在线评测系统POJ的编程题目,该题目主要涉及深度优先搜索(DFS)算法和强剪枝策略。在算法竞赛和编程挑战中,这类问题通常要求参赛者通过编写...

    POJ3009-Curling 2.0【DFS+Vector+回溯+剪枝】

    1. **深度优先搜索(DFS)**:DFS是一种遍历或搜索树或图的算法,用于在所有可能的路径中寻找目标路径。在Curling 2.0问题中,DFS常用于遍历所有可能的游戏状态,以便找出最佳的决策序列。通过递归调用或者栈来实现...

    ACM-POJ 算法训练指南

    1. **状态转移方程**:设计复杂的动态规划状态转移方程(poj1191, poj1054, poj3280, poj2029, poj2948, poj1925, poj3034)。 2. **记忆化搜索**:结合动态规划和递归搜索(POJ3254, poj2411, poj1185)。 3. **...

    状态压缩DP

    例如,在0/1背包问题中,状态转移方程为`dp[i][j] = max(dp[i-1][j], dp[i-1][j-w[i]] + v[i])`,其中`w[i]`是第i个物品的重量,`v[i]`是第i个物品的价值。 #### 四、状态压缩动态规划的应用场景 **1. 棋盘问题** ...

    POJ1691-Painting A Board 【拓扑+DFS】

    【标题】"POJ1691-Painting A Board 【拓扑+DFS】"是一个源自北京大学在线编程平台POJ的编程题目,它主要涉及到图论中的拓扑排序和深度优先搜索(DFS)算法。该题目的核心是解决一个与涂色相关的实际问题,通过运用...

    POJ1015-Jury Compromise【动态规划DP】

    总的来说,解决"POJ1015-Jury Compromise"这个问题,我们需要深入理解动态规划的基本原理,能够根据问题的特点设计合适的状态和状态转移方程,然后用编程语言如C++实现算法,最后通过编写解题报告来清晰地表达解决...

    poj2488——dfs深度优先遍历

    poj 2488——dfs深度优先遍历 //给行数列数,求问能否遍历,给出字典序的一种遍历

    poj训练计划.doc

    - 记录状态的动态规划:如`poj3254, poj2411`。 这份训练计划不仅涵盖了基础的算法和数据结构,还深入到了更复杂的概念和技巧,如图算法中的差分约束系统、最小费用最大流,以及数据结构中的线段树和RMQ。此外,还...

    强大的poj分类

    ### 强大的POJ分类解析 #### 一、引言 POJ(Peking Online Judge)作为中国最早的一批在线编程评测系统之一,为广大学习算法与数据结构的同学提供了丰富的资源。它不仅包含了各类经典的算法题目,还通过详细的分类...

    poj1691解题报告

    ### poj1691解题报告 #### 题目信息 - **题目名称**:Painting A Board - **时间限制**:1S - **内存限制**:1000K - **提交总数**:62 - **通过总数**:35 - **来源**:...

    poj_dp分类

    ### poj_dp分类解析 #### 概述 在本篇文章中,我们将深入探讨并解析PoJ (Pacific Ocean Judger) 平台上与动态规划(Dynamic Programming, DP)相关的题目分类及其特征。通过这些题目,读者可以更好地理解动态规划的...

    Poj动态规划题目列表

    状态转移方程为`dp_max[i] = max(dp_max[i-1]*a[i], dp_min[i-1]*a[i], a[i])` 和 `dp_min[i] = min(dp_max[i-1]*a[i], dp_min[i-1]*a[i], a[i])`。 #### 3. POJ 1143 - Number Game - **题目描述**:有两个玩家...

Global site tag (gtag.js) - Google Analytics