You are given an m x n integer matrix points (0-indexed). Starting with 0 points, you want to maximize the number of points you can get from the matrix.
To gain points, you must pick one cell in each row. Picking the cell at coordinates (r, c) will add points[r][c] to your score.
However, you will lose points if you pick a cell too far from the cell that you picked in the previous row. For every two adjacent rows r and r + 1 (where 0 <= r < m - 1), picking cells at coordinates (r, c1) and (r + 1, c2) will subtract abs(c1 - c2) from your score.
Return the maximum number of points you can achieve.
abs(x) is defined as:
x for x >= 0.-x for x < 0.Example 1:
Input: points = [[1,2,3],[1,5,1],[3,1,1]] Output: 9 Explanation: The blue cells denote the optimal cells to pick, which have coordinates (0, 2), (1, 1), and (2, 0). You add 3 + 5 + 3 = 11 to your score. However, you must subtract abs(2 - 1) + abs(1 - 0) = 2 from your score. Your final score is 11 - 2 = 9.
Example 2:
Input: points = [[1,5],[2,3],[4,2]] Output: 11 Explanation: The blue cells denote the optimal cells to pick, which have coordinates (0, 1), (1, 1), and (2, 0). You add 5 + 3 + 4 = 12 to your score. However, you must subtract abs(1 - 1) + abs(1 - 0) = 1 from your score. Your final score is 12 - 1 = 11.
Constraints:
m == points.lengthn == points[r].length1 <= m, n <= 1051 <= m * n <= 1050 <= points[r][c] <= 105When 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:
The brute force method for maximizing points with cost simply tries every possible path. It considers all possible column choices for each row to find the path that results in the maximum score. This approach guarantees finding the optimal solution, but it is not the most efficient.
Here's how the algorithm would work step-by-step:
def max_points_brute_force(points):
number_of_rows = len(points)
number_of_columns = len(points[0])
# Initialize scores for the first row
scores = points[0]
# Iterate through the remaining rows
for row_index in range(1, number_of_rows):
new_scores = [0] * number_of_columns
for column_index in range(number_of_columns):
# Find the best score from the previous row
max_score = 0
for previous_column_index in range(number_of_columns):
cost = abs(column_index - previous_column_index)
current_score = scores[previous_column_index] - cost
#Need to find the highest possible score from the previous row
max_score = max(max_score, current_score)
#Add to score for current position
new_scores[column_index] = max_score + points[row_index][column_index]
scores = new_scores
#Need to check if scores is empty or not.
if not scores:
return 0
#After the entire array has been calculated, find the highest score
maximum_points = max(scores)
return maximum_pointsWe want to find the path that gives us the most points, but subtracting costs as we move. The key is to efficiently track the best possible score we can achieve at each position as we go through the grid, avoiding re-computation of scores.
Here's how the algorithm would work step-by-step:
def maximum_points(points):
rows = len(points)
cols = len(points[0])
previous_row_points = points[0][:]
for row_index in range(1, rows):
current_row_points = [0] * cols
# Calculate best possible score at each cell.
for col_index in range(cols):
for previous_col_index in range(cols):
cost = abs(col_index - previous_col_index)
current_points = previous_row_points[previous_col_index] - cost + points[row_index][col_index]
current_row_points[col_index] = max(current_row_points[col_index], current_points)
previous_row_points = current_row_points
# The maximum points will be at the last row.
return max(previous_row_points)| Case | How to Handle |
|---|---|
| Empty or null `points` array | Return 0 immediately as there are no points to collect. |
| Empty or null `cost` array | Return 0 if the `cost` array is empty or null, as there's no cost to calculate points with. |
| Single row in `points` array | Return the maximum value in the first row since there's no cost to consider for other rows. |
| All values in a row are identical | Algorithm should correctly handle this without performance issues; the cost calculation is the key part. |
| Maximum integer values in `points` array (potential overflow) | Use `long` data type to store intermediate sums and the result to avoid potential integer overflow issues when calculating the maximum points. |
| Large input size (rows * columns exceeding memory limits) | Optimize memory usage by only storing the previous row's DP values to avoid storing the entire DP table. |
| Negative values in cost array | Ensure the logic correctly handles negative costs, potentially making a row transition *more* beneficial if the point difference isn't too great. |
| Cost is zero for all transitions | This simplifies the problem to finding the maximum sum of points in each row, as row transitions are essentially free. |