Find all rectangles filled with 0 - GeeksforGeeks

08 Mar, 2022
We have one 2D array, filled with zeros and ones. We have to find the starting point and ending point of all rectangles filled with 0. It is given that rectangles are separated and do not touch each other however they can touch the boundary of the array.A rectangle might contain only one element.Examples:  
input = [
            [1, 1, 1, 1, 1, 1, 1],
            [1, 1, 1, 1, 1, 1, 1],
            [1, 1, 1, 0, 0, 0, 1],
            [1, 0, 1, 0, 0, 0, 1],
            [1, 0, 1, 1, 1, 1, 1],
            [1, 0, 1, 0, 0, 0, 0],
            [1, 1, 1, 0, 0, 0, 1],
            [1, 1, 1, 1, 1, 1, 1]
        ]


Output:
[
  [2, 3, 3, 5], [3, 1, 5, 1], [5, 3, 6, 5]
]

Explanation:
We have three rectangles here, starting from 
(2, 3), (3, 1), (5, 3)

Input = [
            [1, 0, 1, 1, 1, 1, 1],
            [1, 1, 0, 1, 1, 1, 1],
            [1, 1, 1, 0, 0, 0, 1],
            [1, 0, 1, 0, 0, 0, 1],
            [1, 0, 1, 1, 1, 1, 1],
            [1, 1, 1, 0, 0, 0, 0],
            [1, 1, 1, 1, 1, 1, 1],
            [1, 1, 0, 1, 1, 1, 0]
        ]


Output:
[
  [0, 1, 0, 1], [1, 2, 1, 2], [2, 3, 3, 5], 
  [3, 1, 4, 1], [5, 3, 5, 6], [7, 2, 7, 2], 
  [7, 6, 7, 6]
]
 
Step 1: Look for the 0 row-wise and column-wiseStep 2: When you encounter any 0, save its position in output array and using loop change all related 0 with this position in any common number so that we can exclude it from processing next time.Step 3: When you change all related 0 in Step 2, store last processed 0’s location in output array in the same index.Step 4: Take Special care when you touch the edge, by not subtracting -1 because the loop has broken on the exact location. Below is the implementation of above approach:  
C++
Python3
Javascript
// C++ program for the above approach#include <bits/stdc++.h>using namespace std; void findend(int i,int j, vector<vector<int>> &a,             vector<vector<int>> &output,int index){  int x = a.size();  int y = a[0].size();   // flag to check column edge case,  // initializing with 0  int flagc = 0;   // flag to check row edge case,  // initializing with 0  int flagr = 0;  int n, m;   for (m = i; m < x; m++)  {     // loop breaks where first 1 encounters    if (a[m][j] == 1)    {      flagr = 1; // set the flag      break;    }     // pass because already processed    if (a[m][j] == 5) continue;     for (n = j; n < y; n++)    {      // loop breaks where first 1 encounters      if (a[m][n] == 1)      {        flagc = 1; // set the flag        break;      }       // fill rectangle elements with any      // number so that we can exclude      // next time      a[m][n] = 5;    }  }   if (flagr == 1)    output[index].push_back(m-1);  else    // when end point touch the boundary    output[index].push_back(m);   if (flagc == 1)    output[index].push_back(n-1);  else    // when end point touch the boundary    output[index].push_back(n);} void get_rectangle_coordinates(vector<vector<int>> a){   // retrieving the column size of array  int size_of_array = a.size();   // output array where we are going  // to store our output  vector<vector<int>> output;   // It will be used for storing start  // and end location in the same index  int index = -1;   for (int i = 0; i < size_of_array; i++)  {    for (int j = 0; j < a[0].size(); j++)    {      if (a[i][j] == 0)      {         // storing initial position        // of rectangle        output.push_back({i, j});         // will be used for the        // last position        index = index + 1;        findend(i, j, a, output, index);      }    }  }   cout << "[";  int aa = 2, bb = 0;   for(auto i:output)  {    bb = 3;    cout << "[";    for(int j:i)    {      if(bb)        cout << j << ", ";      else        cout << j;      bb--;    }    cout << "]";    if(aa)      cout << ", ";    aa--;   }  cout << "]";} // Driver codeint main(){  vector<vector<int>> tests = {    {1, 1, 1, 1, 1, 1, 1},    {1, 1, 1, 1, 1, 1, 1},    {1, 1, 1, 0, 0, 0, 1},    {1, 0, 1, 0, 0, 0, 1},    {1, 0, 1, 1, 1, 1, 1},    {1, 0, 1, 0, 0, 0, 0},    {1, 1, 1, 0, 0, 0, 1},    {1, 1, 1, 1, 1, 1, 1}  };   get_rectangle_coordinates(tests);   return 0;} // This code is contributed by mohit kumar 29.
# Python program to find all# rectangles filled with 0 def findend(i,j,a,output,index):    x = len(a)    y = len(a[0])     # flag to check column edge case,    # initializing with 0    flagc = 0     # flag to check row edge case,    # initializing with 0    flagr = 0     for m in range(i,x):         # loop breaks where first 1 encounters        if a[m][j] == 1:            flagr = 1 # set the flag            break         # pass because already processed        if a[m][j] == 5:            pass         for n in range(j, y):             # loop breaks where first 1 encounters            if a[m][n] == 1:                flagc = 1 # set the flag                break             # fill rectangle elements with any            # number so that we can exclude            # next time            a[m][n] = 5     if flagr == 1:        output[index].append( m-1)    else:        # when end point touch the boundary        output[index].append(m)     if flagc == 1:        output[index].append(n-1)    else:        # when end point touch the boundary        output[index].append(n)  def get_rectangle_coordinates(a):     # retrieving the column size of array    size_of_array = len(a)     # output array where we are going    # to store our output    output = []     # It will be used for storing start    # and end location in the same index    index = -1     for i in range(0,size_of_array):        for j in range(0, len(a[0])):            if a[i][j] == 0:                 # storing initial position                # of rectangle                output.append([i, j])                 # will be used for the                # last position                index = index + 1                       findend(i, j, a, output, index)      print (output) # driver codetests = [             [1, 1, 1, 1, 1, 1, 1],            [1, 1, 1, 1, 1, 1, 1],            [1, 1, 1, 0, 0, 0, 1],            [1, 0, 1, 0, 0, 0, 1],            [1, 0, 1, 1, 1, 1, 1],            [1, 0, 1, 0, 0, 0, 0],            [1, 1, 1, 0, 0, 0, 1],            [1, 1, 1, 1, 1, 1, 1]         ]  get_rectangle_coordinates(tests)
<script> // JavaScript program to find all// rectangles filled with 0 function findend(i,j,a,output,index){    let x = a.length    let y = a[0].length    let m,n;     // flag to check column edge case,    // initializing with 0    let flagc = 0     // flag to check row edge case,    // initializing with 0    let flagr = 0     for(m=i;m<x;m++){         // loop breaks where first 1 encounters        if(a[m][j] == 1){            flagr = 1 // set the flag            break        }         // pass because already processed        if(a[m][j] == 5)            pass         for(n=j;n<y;n++){             // loop breaks where first 1 encounters            if(a[m][n] == 1){                flagc = 1 // set the flag                break            }             // fill rectangle elements with any            // number so that we can exclude            // next time            a[m][n] = 5        }    }     if(flagr == 1)        output[index].push( m-1)    else        // when end point touch the boundary        output[index].push(m)     if(flagc == 1)        output[index].push(n-1)    else        // when end point touch the boundary        output[index].push(n)} function get_rectangle_coordinates(a){     // retrieving the column size of array    let size_of_array = a.length     // output array where we are going    // to store our output    let output = []     // It will be used for storing start    // and end location in the same index    let index = -1     for(let i=0;i<size_of_array;i++){        for(let j=0;j<a[0].length;j++){            if(a[i][j] == 0){                 // storing initial position                // of rectangle                output.push([i, j])                 // will be used for the                // last position                index = index + 1                   findend(i, j, a, output, index)            }        }    }     console.log(output)} // driver codelet tests = [             [1, 1, 1, 1, 1, 1, 1],            [1, 1, 1, 1, 1, 1, 1],            [1, 1, 1, 0, 0, 0, 1],            [1, 0, 1, 0, 0, 0, 1],            [1, 0, 1, 1, 1, 1, 1],            [1, 0, 1, 0, 0, 0, 0],            [1, 1, 1, 0, 0, 0, 1],            [1, 1, 1, 1, 1, 1, 1]         ]  get_rectangle_coordinates(tests) // This code is contributed by shinjanpatra </script>
Output:
[[2, 3, 3, 5], [3, 1, 5, 1], [5, 3, 6, 5]]
This article is contributed by Prabhat jha. If you like GeeksforGeeks and would like to contribute, you can also write an article using write.geeksforgeeks.org or mail your article to review-team@geeksforgeeks.org. See your article appearing on the GeeksforGeeks main page and help other Geeks.Please write comments if you find anything incorrect, or you want to share more information about the topic discussed above. Asked in Intuit 
mohit kumar 29
shinjanpatra
square-rectangle
Matrix
Matrix
Writing code in comment?
Please use ide.geeksforgeeks.org,
generate link and share the link here.
Divide and Conquer | Set 5 (Strassen's Matrix Multiplication)
Sudoku | Backtracking-7
Program to multiply two matrices
Inplace rotate square matrix by 90 degrees | Set 1
The Celebrity Problem
Count all possible paths from top left to bottom right of a mXn matrix
Python program to multiply two matrices
Printing all solutions in N-Queen Problem
Rotate a matrix by 90 degree in clockwise direction without using any extra space
Maximum size rectangle binary sub-matrix with all 1s