There is a row of n
houses, where each house can be painted one of three colors: red, blue, or green. The cost of painting each house with a certain color is different. You have to paint all the houses such that no two adjacent houses have the same color.
The cost of painting each house with a certain color is represented by an n x 3
cost matrix costs
.
costs[0][0]
is the cost of painting house 0
with the color red; costs[1][2]
is the cost of painting house 1
with color green, and so on...Return the minimum cost to paint all houses.
Example 1:
Input: costs = [[17,2,17],[16,16,5],[14,3,19]]
Output: 10
Explanation: Paint house 0 into blue, paint house 1 into green, paint house 2 into blue.
Minimum cost: 2 + 5 + 3 = 10.
Example 2:
Input: costs = [[7,6,2]]
Output: 2
Constraints:
costs.length == n
costs[i].length == 3
1 <= n <= 100
1 <= costs[i][j] <= 100
When you get asked this question in a real-life environment, it will often be ambiguous (especially at FAANG). Make sure to ask these questions in that case:
We need to find the cheapest way to paint a row of houses, where each house can be painted one of several colors, and each color has a different cost. The brute force approach explores every single possible color combination for all the houses. We then calculate the total cost for each combination and pick the cheapest one.
Here's how the algorithm would work step-by-step:
def paint_house_brute_force(costs):
number_of_houses = len(costs)
if number_of_houses == 0:
return 0
minimum_cost = float('inf')
def calculate_total_cost(color_choices):
total_cost = 0
for house_index, color_index in enumerate(color_choices):
total_cost += costs[house_index][color_index]
return total_cost
def find_minimum_cost(house_index, current_color_choices):
nonlocal minimum_cost
# Base case: all houses have been painted
if house_index == number_of_houses:
total_cost_for_choices = calculate_total_cost(current_color_choices)
minimum_cost = min(minimum_cost, total_cost_for_choices)
return
# Try painting the current house each possible color
number_of_colors = len(costs[house_index])
for color_index in range(number_of_colors):
# Recursively call function with added color
find_minimum_cost(house_index + 1, current_color_choices + [color_index])
# Start the recursion from the first house with empty color choices
find_minimum_cost(0, [])
return minimum_cost
The core idea is to minimize the cost of painting each house by considering the costs of the previous houses. Instead of checking every possible color combination, we'll use past information to build up to the best solution one house at a time.
Here's how the algorithm would work step-by-step:
def paint_house(costs):
if not costs:
return 0
number_of_houses = len(costs)
# Iterate through houses, updating costs based on min from prev
for i in range(1, number_of_houses):
# Update cost for red. We're finding the min cost so far.
costs[i][0] += min(costs[i - 1][1], costs[i - 1][2])
# Update cost for blue
costs[i][1] += min(costs[i - 1][0], costs[i - 1][2])
# Update cost for green
costs[i][2] += min(costs[i - 1][0], costs[i - 1][1])
# The minimum cost will be the smallest of the costs for the last house.
return min(costs[number_of_houses - 1][0], costs[number_of_houses - 1][1], costs[number_of_houses - 1][2])
Case | How to Handle |
---|---|
Null or empty costs array | Return 0 since there are no houses to paint. |
Costs array with zero rows (zero houses) | Return 0 since no painting is needed. |
Costs array with one row (one house) | Return the minimum cost among the three colors for that single house. |
Costs array with all colors for a house having the same cost | The algorithm should still correctly find the minimum total cost, potentially requiring tie-breaking logic. |
Large costs that could potentially lead to integer overflow when summing | Use a larger integer data type (e.g., long) to store intermediate and final results. |
Costs array with extremely large dimensions (many houses) | The dynamic programming approach should have O(n) space complexity where n is the number of houses, so it should scale adequately. |
Costs array contains negative costs | The problem statement doesn't define negative costs, so the code should either throw an error or assume the absolute values are intended. |
Only 1 color available | If the costs array has only 1 column, it means only one color is available; then just sum all the color values. |