The K Weakest Rows in a Matrix

Updated on 10 July, 2025
The K Weakest Rows in a Matrix header image

Problem Statement

In the given problem, you are presented with a matrix labeled mat where each element is exclusively a 1 or a 0. These numbers symbolize the presence of soldiers and civilians respectively, within a structured layout where all soldiers (1s) are arranged to the left of all civilians (0s) within any given row. The matrix dimensions are defined by m rows and n columns.

The objective here is to identify the "weakness" level of each row, measured by the count of soldiers (1s). A row i is deemed weaker than another row j if it has fewer soldiers than j, or if they have the same number of soldiers but i is positioned earlier (has a lower index) than j. Your goal is to return a list containing the indices of the k weakest rows sorted from the weakest to the strongest.

Examples

Example 1

Input:

mat =
[[1,1,0,0,0],
[1,1,1,1,0],
[1,0,0,0,0],
[1,1,0,0,0],
[1,1,1,1,1]],
k = 3

Output:

[2,0,3]

Explanation:

The number of soldiers in each row is:
- Row 0: 2
- Row 1: 4
- Row 2: 1
- Row 3: 2
- Row 4: 5
The rows ordered from weakest to strongest are [2,0,3,1,4].

Example 2

Input:

mat =
[[1,0,0,0],
[1,1,1,1],
[1,0,0,0],
[1,0,0,0]],
k = 2

Output:

[0,2]

Explanation:

The number of soldiers in each row is:
- Row 0: 1
- Row 1: 4
- Row 2: 1
- Row 3: 1
The rows ordered from weakest to strongest are [0,2,3,1].

Constraints

  • m == mat.length
  • n == mat[i].length
  • 2 <= n, m <= 100
  • 1 <= k <= m
  • matrix[i][j] is either 0 or 1.

Approach and Intuition

To solve the problem, the approach can be outlined through the following steps:

  1. Count soldiers in each row: Traverse through each row and count the number of soldiers (1s). We halt this counting as soon as we encounter a civilian (0) given the sorted-property of each row.

  2. Pair indices with soldier counts: Pair each row number (or index) with its corresponding soldier count. For instance, if the third row has 2 soldiers, pair it as (2, 3) where '3' is the row index and '2' is the soldier count.

  3. Sort the pair list: Order this list of pairs primarily by the soldier count in ascending order. If two rows have the same count, the row with a lower index should come first. (Sort by soldier count, and use index as a tie-breaker).

  4. Select the top k entries: Once sorted by weakness, select the first k row indices from this list.

By closely following these operations, even a matrix with the maximum constraints can be handled efficiently due to the structure and distribution of soldiers and civilians in the rows. Additionally, since each row is inspected once and sorting is applied, the combined complexity is dominated by the sorting step, which is generally feasible within the given constraints. The entire approach ensures that we can effectively pinpoint the k weakest rows as intended.

Solutions

  • Java
java
class Solution {
    public int[] getWeakestRows(int[][] grid, int k) {
    
        int rows = grid.length;
        int cols = grid[0].length;
    
        int[] result = new int[k];
        int fillIndex = 0;
    
        for (int col = 0; col < cols && fillIndex < k; col++) {
            for (int row = 0; row < rows && fillIndex < k; row++) {
                if (grid[row][col] == 0 && (col == 0 || grid[row][col - 1] == 1)) {
                    result[fillIndex] = row;
                    fillIndex++;
                }
            }
        }
    
        for (int row = 0; fillIndex < k; row++) {
            if (grid[row][cols - 1] == 1) {
                result[fillIndex] = row;
                fillIndex++;
            }
        }
    
        return result;
    }
}

The provided Java solution identifies the k weakest rows in a binary matrix, where the strength of a row is determined by the earliest occurrence of a '0' (zeroes represent weaknesses). The approach involves scanning the matrix column by column and then row by row, marking a row as weak if an element is 0 and it’s the first in its row or the previous element in the same row is 1. This continues until enough rows have been found or until there are no more columns to inspect.

  • The getWeakestRows method first initializes arrays and variables for tracking results and indices.
  • It then starts a nested loop, where it iterates through columns outermost, checking rows for the first occurrence of 0 under the specified conditions. Each time it confirms a weak row, it records the row index in the result array.
  • If all rows have stronger elements where no 0 occurs before the end of the columns, a secondary loop captures any remaining strongest rows until the result array is filled.

This method efficiently compiles the list of weakest row indices in the result array up to the specified number k, leveraging row and column checks to quickly identify weaker rows based on matrix structure and avoiding full row traversals unless necessary.

Overall, the functionality focuses on effectively returning the list of weakest row indices based on predefined conditions without additional or unnecessary computation.

  • Python
python
def findWeakestRows(self, matrix: List[List[int]], count: int) -> List[int]:
    total_rows = len(matrix)
    total_cols = len(matrix[0])
    
    weakest_rows = []
    # Process each cell in the matrix in specified order.
    for col, row in itertools.product(range(total_cols), range(total_rows)):
        if len(weakest_rows) == count: break
        # Add the row if it is the first 0 or the transition from 1 to 0.
        if matrix[row][col] == 0 and (col == 0 or matrix[row][col - 1] == 1):
            weakest_rows.append(row)
    
    # If not enough weakest rows, add full 1 rows based on their order.
    row_index = 0
    while len(weakest_rows) < count:
        if matrix[row_index][-1] == 1:
            weakest_rows.append(row_index)
        row_index += 1
    
    return weakest_rows

The solution provided is designed to determine the weakest rows in a given binary matrix where the elements of the matrix can either be 0 (representing soldiers) or 1 (representing civilians). "Weakest" in the context refers to rows with the fewest numbers of soldiers (zeros), and the objective is to return these rows in increasing order of their strength up to a specified count.

Here's a breakdown of how the solution functions:

  • Initialize Variables: The total number of rows and columns in the matrix are determined. An empty list weakest_rows is initialized to store the indices of the weakest rows.

  • Identify Rows: Using the itertools.product function, the solution iterates through each cell in the matrix by columns first and then by rows. This method ensures that the rows are checked for weakness (transition from 1 to 0) in a column-wise manner across all rows before moving to the next column:

    • It checks if a cell contains 0, and it is either the first cell in the row or it follows a cell with a 1. If these conditions are met, the row index is added to the weakest_rows list.
    • If the count of weakest_rows reaches the required number (count), the iteration stops.
  • Fill Remaining Slots: If the list weakest_rows hasn’t reached the length specified by count after checking all transitions from 1 to 0:

    • The solution then iterates over the rows again, adding rows filled with 1s to the weakest_rows list until it reaches the required length.
  • Return Result: The weakest_rows list is returned containing the indices of the weakest rows up to the specified count.

This approach efficiently identifies rows based on the prompt’s requirement by first leveraging the transitions within each row and then ensuring that enough rows are returned, even if some rows consist entirely of soldiers.

Comments

No comments yet.