Each week Mohammad S. Anwar sends out The Weekly Challenge, a chance for all of us to come up with solutions to two weekly tasks. It's a great way for us all to practice some coding.
Challenge, My solutions
You are given an m x n binary matrix with 0 and 1 only.
Write a script to find the largest square containing only 1's and return its area.
My main function starts by checking that the matrix has the correct number of columns for each row
def maximal_square(matrix: list[list[int]]) -> int: rows = len(matrix) cols = len(matrix[0]) maximum_size = 0 for row in range(rows): if len(matrix[row]) != cols: raise ValueError("Row %s has the wrong number of columns", row)
It then iterates through each cell in the matrix. If the item in that cell is a 1, it then checks the size of the square starting at that position. The max_side variable is also calculated to ensure we don't go out of bounds. We keep track of the maximum_size value and return the largest one.
for row in range(rows): for col in range(cols): if matrix[row][col] == 1: max_side = min(rows-row, cols-col) size = find_square_from_point(matrix, row, col, max_side) if size > maximum_size: maximum_size = size return maximum_size
The find_square_from_point function was frustrating to get right. I actually had a few goes before I had a solution I was happy on committing. The logic is pretty straight forward. Consider the square:
. b c d b b c d c c c d d d d d
As the size of the square increases, I only need to check the bottom and right side of each square, as I know the inner part of the square has already been checked. So for the first iteration (an area of four), I check the b cells. The next iteration (area of 9), I check the c cells, and so on.
This is the code of the function:
def find_square_from_point(matrix, x: int, y: int, max_side: int) -> int: side = 1 for s in range(1, max_side): all_ones = True for i in range(s+1): if matrix[x+i][y+s] == 0 or matrix[x+s][y+i] == 0: all_ones = False break if not all_ones: break side += 1 return side ** 2
$ ./ch-1.py "[[1, 0, 1, 0, 0],[1, 0, 1, 1, 1],[1, 1, 1, 1, 1],[1, 0, 0, 1, 0]]" 4 $ ./ch-1.py "[[0, 1],[1, 0]]" 1 $ ./ch-1.py "[[0]]" 0
You are given an array of @intervals, where $intervals[i] = [starti, endi] and each starti is unique.
The right interval for an interval i is an interval j such that startj >= endi and startj is minimized. Please note that i may equal j.
Write a script to return an array of right interval indices for each interval i. If no right interval exists for interval i, then put -1 at index i.
For this task, I have a solution that works, but I'm not convinced it is the most efficient. For each interval, I set three variables:
I then have an inner loop that iterates over the intervals. If the start_j value (first value in the interval) is greater than or equal to end_i and is lower than lowest_j, I update the lowest_j and index_j values.
def maximal_square(matrix: list[list[int]]) -> int: rows = len(matrix) cols = len(matrix[0]) maximum_size = 0 for row in range(rows): if len(matrix[row]) != cols: raise ValueError("Row %s has the wrong number of columns", row)
For inputs from the command line, I take a list of integers and pair them up automatically.
for row in range(rows): for col in range(cols): if matrix[row][col] == 1: max_side = min(rows-row, cols-col) size = find_square_from_point(matrix, row, col, max_side) if size > maximum_size: maximum_size = size return maximum_size
The above is the detailed content of Maximizing the interval. For more information, please follow other related articles on the PHP Chinese website!