leetcode 174. 地下城游戏 解题报告
leetcode 174. 地下城游戏
一些恶魔抓住了公主(P)并将她关在了地下城的右下角。地下城是由 M x N 个房间组成的二维网格。我们英勇的骑士(K)最初被安置在左上角的房间里,他必须穿过地下城并通过对抗恶魔来拯救公主。
骑士的初始健康点数为一个正整数。如果他的健康点数在某一时刻降至 0 或以下,他会立即死亡。
有些房间由恶魔守卫,因此骑士在进入这些房间时会失去健康点数(若房间里的值为负整数,则表示骑士将损失健康点数);其他房间要么是空的(房间里的值为 0),要么包含增加骑士健康点数的魔法球(若房间里的值为正整数,则表示骑士将增加健康点数)。
为了尽快到达公主,骑士决定每次只向右或向下移动一步。
| -2 (K) | -3 | 3 |
| -5 | -10 | 1 |
| 10 | 30 | -5 (P) |
编写一个函数来计算确保骑士能够拯救到公主所需的最低初始健康点数。
例如,考虑到如下布局的地下城,如果骑士遵循最佳路径 右 -> 右 -> 下 -> 下,则骑士的初始健康点数至少为 7。
说明:
骑士的健康点数没有上限。
任何房间都可能对骑士的健康点数造成威胁,也可能增加骑士的健康点数,包括骑士进入的左上角房间以及公主被监禁的右下角房间。
分析
根据题目的描述,这道题目是动态规划无疑。但是如何建立递推关系表达式呢?我们令dp[i][j]表示从(i,j)出发到公主所在位置所需的最小的初始血量。那么dp[0][0]+1即为救出公主所需的最小初始健康值。因为骑士的健康值在任何时候都不能低于1,所以此处加了1。下面我们分析下地推关系。我们知道骑士可以往下走或者往右走。如果\(dungeon[i][j] \ge dp[i][j+1]\),那么由\((i,j)\rightarrow (i,j+1)\),由\(dungeon[i][j]\)提供的魔法球增加的健康值足够骑士走到公主所在位置,不需要补给额外的能量。否则,则需要提供额外的健康值\(dp[i][j+1] - dungeon[i][j]\)才足以维持骑士的生命。由\((i,j)\rightarrow (i+1,j)\)也是同理,于是我们有如下的表达
\]
上式可以保证在任何时候\(dp[i][j]\ge 0\)。
下面给出代码
class Solution {
public:
int calculateMinimumHP(vector<vector<int>>& dungeon) {
const int m = dungeon.size();
const int n = dungeon[0].size();
int dp[m][n] = {};
dp[m-1][n-1] = dungeon[m-1][n-1] >= 0?0:-dungeon[m-1][n-1];
for(int i = m-1; i >= 0; --i) {
for(int j = n-1; j >= 0; --j) {
int ret = 0x3f3f3f3f;
if(i < m - 1)
ret = min(ret, dp[i+1][j] - dungeon[i][j]);
if(j < n - 1)
ret = min(ret, dp[i][j+1] - dungeon[i][j]);
if (i < m - 1 or j < n - 1)
dp[i][j] = max(0, ret);
}
}
return dp[0][0] + 1;
}
};
leetcode 174. 地下城游戏 解题报告的更多相关文章
- Java实现 LeetCode 174 地下城游戏
174. 地下城游戏 一些恶魔抓住了公主(P)并将她关在了地下城的右下角.地下城是由 M x N 个房间组成的二维网格.我们英勇的骑士(K)最初被安置在左上角的房间里,他必须穿过地下城并通过对抗恶魔来 ...
- Leetcode 174.地下城游戏
地下城游戏 一些恶魔抓住了公主(P)并将她关在了地下城的右下角.地下城是由 M x N 个房间组成的二维网格.我们英勇的骑士(K)最初被安置在左上角的房间里,他必须穿过地下城并通过对抗恶魔来拯救公主. ...
- LeetCode 1 Two Sum 解题报告
LeetCode 1 Two Sum 解题报告 偶然间听见leetcode这个平台,这里面题量也不是很多200多题,打算平时有空在研究生期间就刷完,跟跟多的练习算法的人进行交流思想,一定的ACM算法积 ...
- 【LeetCode】Permutations II 解题报告
[题目] Given a collection of numbers that might contain duplicates, return all possible unique permuta ...
- 【LeetCode】Island Perimeter 解题报告
[LeetCode]Island Perimeter 解题报告 [LeetCode] https://leetcode.com/problems/island-perimeter/ Total Acc ...
- 【LeetCode】01 Matrix 解题报告
[LeetCode]01 Matrix 解题报告 标签(空格分隔): LeetCode 题目地址:https://leetcode.com/problems/01-matrix/#/descripti ...
- 【LeetCode】Largest Number 解题报告
[LeetCode]Largest Number 解题报告 标签(空格分隔): LeetCode 题目地址:https://leetcode.com/problems/largest-number/# ...
- 【LeetCode】Gas Station 解题报告
[LeetCode]Gas Station 解题报告 标签(空格分隔): LeetCode 题目地址:https://leetcode.com/problems/gas-station/#/descr ...
- 【LeetCode】120. Triangle 解题报告(Python)
[LeetCode]120. Triangle 解题报告(Python) 作者: 负雪明烛 id: fuxuemingzhu 个人博客: http://fuxuemingzhu.cn/ 题目地址htt ...
随机推荐
- 【转】Android tools:context
tools:context="com.example.guolin.scrollertest.MainActivity" 有时候可以看到有这个东西,但是从来没有用过,不知道有什么作 ...
- Xamarin.Forms随手记
1. 更新Android SDK要从VS的工具栏上SDK Manager那里更新,不要像我一样之前搞了好几份SDK放在不同的地方,结果把自己搞糊涂了,更新了半天(真的是花了半天时间)才发现更新的地方不 ...
- Windows 7下的ARP
关于Windows 7和Windows XP下的ARP绑定的不同之处网络上已经很多,没空就不多说,注意用这样的方式绑定的arp项是动态的,动态的意思就是这个项不受任何保护,Windows想什么时候更改 ...
- 文本编辑器Vim技巧
1. 导入文件内容 :r 文件名 2. 插入当前日期 :r !date 3. :!which ls 4. :r !命令
- Eclipse Python插件 PyDev
PyDev for Eclipse 是一个功能强大且易用的 Eclipse Python IDE 插件.本文将向读者介绍 PyDev 开源项目及其安装配置方法,并在此基础上详细介绍如何利用 PyDev ...
- 移除input number上的spinner
HTML 5 的表单中有着丰富的input种类,比如说input[type="number"],就可以保证用户输入数字,但是input也有一些不好的地方——带有 spinner. ...
- js另类值交换
当我们有a.b两个值,想要交换,通常是要声明第三个变量,但是我最近看到这样一种不用声明第三个变量的处理方法: var a=1,b=2; a=[b,b=a][0]; 其实还是在内存中开出了一个新的空间( ...
- top小火箭
// my.js function $(id){return document.getElementById(id)};function show(obj){obj.style.display = & ...
- Linux中用户与用户组管理
1.基础知识 Linux作为一种多用户的操作系统(服务器系统),允许多个用户同时登陆到系统上,并响应每个用户的请求. 任何需要使用操作系统的用户,都需要一个系统账号,账号分为:管理员账号与普通用户账号 ...
- Shell学习——数组
1.普通数组:只能用整数作为索引1.1.赋值[root@client02 ~]# array[0]=test1[root@client02 ~]# array[1]=test2[root@client ...