持续创作,加速成长!这是我参与「掘金日新计划 · 6 月更文挑战」的第28天,点击查看活动详情
说在前面
🎈每天进行一道算法题目练习,今天的题目是“剑指 Offer II 091. 粉刷房子”,一起来看看这道简单的动态规划题目。
问题描述
假如有一排房子,共 n 个,每个房子可以被粉刷成红色、蓝色或者绿色这三种颜色中的一种,你需要粉刷所有的房子并且使其相邻的两个房子颜色不能相同。
当然,因为市场上不同颜色油漆的价格不同,所以房子粉刷成不同颜色的花费成本也是不同的。每个房子粉刷成不同颜色的花费是以一个 n x 3 的正整数矩阵 costs 来表示的。
例如,costs[0][0] 表示第 0 号房子粉刷成红色的成本花费;costs[1][2] 表示第 1 号房子粉刷成绿色的花费,以此类推。
请计算出粉刷完所有房子最少的花费成本。
示例 1:
输入: costs = [[17,2,17],[16,16,5],[14,3,19]]
输出: 10
解释: 将 0 号房子粉刷成蓝色,1 号房子粉刷成绿色,2 号房子粉刷成蓝色。
最少花费: 2 + 5 + 3 = 10。
示例 2:
输入: costs = [[7,6,2]]
输出: 2
提示:
costs.length == n
costs[i].length == 3
1 <= n <= 100
1 <= costs[i][j] <= 20
思路分析
这是一道简单的动态规划题目,题目的意思是相邻两两个房子不可以是一样的颜色,也就是说房子染的颜色与上一个房子染的颜色是有关系的,当前位置的房子可以染的颜色会被上一个房子所影响,这就是一道经典的dp入门题目,我们可以这样想:
假设我们当前位于第i个房子,那么当前房子可以染的颜色应该会被第i-1个房子的颜色影响:
如果当前房子想要染成红色,那么上一个房子的颜色只能是绿色或者蓝色;
如果当前房子想要染成绿色,那么上一个房子的颜色只能是红色或者蓝色;
如果当前房子想要染成蓝色,那么上一个房子的颜色只能是绿色或者红色。
所以我们可以得出这样的动态转移方程:
costs[i][0] = Math.min(costs[i - 1][1],costs[i - 1][2]) + costs[i][0];
costs[i][1] = Math.min(costs[i - 1][0],costs[i - 1][2]) + costs[i][1];
costs[i][2] = Math.min(costs[i - 1][1],costs[i - 1][0]) + costs[i][2];
第一个房子可以选择染成红蓝绿任意一种颜色,后面的按照动态转移方程,并且计算出染色的最小代价即可,具体代码如下:
AC代码
/**
* @param {number[][]} costs
* @return {number}
*/
var minCost = function(costs) {
for(let i = 1; i < costs.length; i++){
costs[i][0] = Math.min(costs[i - 1][1],costs[i - 1][2]) + costs[i][0];
costs[i][1] = Math.min(costs[i - 1][0],costs[i - 1][2]) + costs[i][1];
costs[i][2] = Math.min(costs[i - 1][1],costs[i - 1][0]) + costs[i][2];
}
return Math.min(...costs[costs.length - 1]);
};
说在后面
🎉这里是JYeontu,喜欢算法,GDCPC打过卡;热爱羽毛球,大运会打过酱油。毕业一年,两年前端开发经验,目前担任H5前端开发,算法业余爱好者,有空会刷刷算法题,平时喜欢打打羽毛球🏸 ,也喜欢写些东西,既为自己记录📋,也希望可以对大家有那么一丢丢的帮助,写的不好望多多谅解🙇,写错的地方望指出,定会认真改进😊,在此谢谢大家的支持,我们下文再见🙌。