Find circles containing only zeros in an arbitrary binary matrix - algorithm

Given a binary matrix of arbitrary size, I need to find circles which fit into this matrix and only cover "0"-fields and no "-1"-fields.
For this example
1 0 0 0 0 1 1
1 0 0 0 0 0 1
1 0 0 0 0 0 1
1 0 0 0 0 0 1
1 0 0 0 0 1 1
I want to find the following maximal circle (denoted in +)
1 0 0 + 0 1 1
1 0 + + + 0 1
1 + + + + + 1
1 0 + + + 0 1
1 0 0 + 0 1 1
Actually this is no circle, only an approximation of it. Finding rectangles in such a binary matrix can be done with the help of histograms, see here. Additionally, I try to find smaller circles like this one:
1 0 + 0 0 1 1 1 0 0 0 0 1 1
1 + + + 0 0 1 1 0 0 0 0 0 1
1 0 + 0 0 0 1 or this one 1 0 0 + 0 0 1
1 0 0 0 0 0 1 1 0 + + + 0 1
1 0 0 0 0 1 1 1 0 0 + 0 0 1
Does anybody have a smart idea (like the histogram-approach for rectangles) of how to identify these circles (or its discrete approximations, respectively)?

Perform a nearest neighbour search, for each 0 element to find the closest 1 element, using Euclidean distance and create another matrix storing the distance from each to the nearest 1 (or just keep track of the largest).
The space that can fit the largest circle will be given by the element with the largest distance to the nearest neighbour, and the distance for each element will specify the size of the circle that can fit in the space centered on that element (distance of 1, means a single +, distance of two means a simple cross, etc).
Note this only works for circles that are centered on a given element. It won't handle circles that are centered part-way between one element and another.

Step1:
start iteration through one by one elements
1.1 : If the element is 0
1.1.1 : check if it in the border , ie, row = 0 or row = max_row or col = 0 or col = max_col
1.1.2 : if not so, check if bottom , top, left and right elements are 0
1.1.3 : if all are 0, increment radius
1.1.4 : else break;
1.1.5: now check bottom-1, top+1, left-1; right+1 to see if they are 0
1.1.6: if they are also 0, again increment radius
1.1.7: repeat the above steps till you break
1.2 : check all elements of matrix

Related

Find the largest chessboard surface in 2D Matrix

I'm having a bit of difficulty by solving an exercise, hope I can get some help from you.
Given a 2D Array with N rows and M columns, and the array has only elements with the value 0 and 1.
Find the largest surface that is similar to a chessboard(where 0 are the white squares and 1 the black squares) and print the size of the surface(number of squares).
Constraints:
2<=N<=1000
2<=M<=1000
Example:
N=4, M=5
0 1 1 0 1
1 0 1 0 1
0 0 1 1 0
1 1 0 1 1
Output: Number of squares=5 (row 2-from column 1 to column 5)
Example:
N=3, M=4
0 0 1 0
1 1 0 0
1 0 1 0
Output: Number of squares=6 (from row 1 to row 3- from column 2 to column 3)
Flip every second cell in a checkerboard pattern
Find the largest rectangle containing only 0s or only 1s.
See Find largest rectangle containing only zeros in an N×N binary matrix for help on the 2nd part.
For your second example:
0 0 1 0
1 1 0 0
1 0 1 0
flipping every 2nd cell produces:
0 1 1 1
0 1 1 0
1 1 1 1
And you can see the rectangle of 1s that you're looking for.

How to calculate the max number of evenly spaced points on a grid

I need to create a grid that has x columns, y rows, where each cell in the grid can have a point in it, and each point is at least z horizontal/vertical spaces away from all other points.
1) Is there a simple method to calculate the maximum number of points I can place given the grid size and a spacing of z?
Here's an example 5x5 with z = 2. In this case the max number of points is 13.
1 0 1 0 1
0 1 0 1 0
1 0 1 0 1
0 1 0 1 0
1 0 1 0 1
and here's an example 5x5 where z = 3. In this case the max number of points is 6.
1 0 0 1 0
0 0 0 0 0
0 1 0 0 1
0 0 0 0 0
1 0 0 1 0
I'd like to be able, given x, y, and z, the number of points possible to plot.
2) What's the most efficient way of populating the grid in this manner?

Find cluster boundary in given matrix

Given matrix contains many clusters. Cluster is represented by 1's.
For Example:
0 1 1 1 0
1 1 1 0 0
0 0 0 1 1
1 1 0 0 1
In this example, there are 3 clusters (connected 1's horizontally or vertically).
Now suppose that matrix size is very big and it contains too many clusters.
Now my question is, I want to know the boundary of all the clusters.
For example given matrix:
0 0 1 1 0
0 1 1 1 1
0 0 1 1 0
0 0 0 1 0
Now output should be coordinates of bold locations:
0 0 1 1 0
0 1 1 1 1
0 0 1 1 0
0 0 0 1 0
Consider matrix is huge with many such clusters, suggest optimized way of finding boundaries of all clusters.
A 1 is on the boundary of some cluster only when it has an 0 as one of its immediate neighbors or when it's on the outline of the matrix, so the naive method would be outputting the coordinates of 1's on the outline, then going through all the other matrix cells and outputting the coordinates of 1's satisfying the said condition.
It doesn't look like there is a way to optimize this algorithm, though.
Suppose we have a huge matrix with only one random 1 inside it. There is no way to find it without going through each and every cell out there.
There is also no way to skip 1's of the same cluster by following the outline of it.
Consider this example:
0 0 0 1 1 1 1 1 1 1
0 0 0 1 0 0 0 0 0 1
0 1 1 1 1 1 0 1 0 1
0 0 0 0 0 1 0 0 0 1
0 0 0 0 0 1 1 1 1 1
One cluster can easily fit inside another one, so following the outline is not an option.

How to create a symmetric matrix of 1's and 0's with constant row and column sum

I'm trying to find an elegant algorithm for creating an N x N matrix of 1's and 0's, under the restrictions:
each row and each column must sum to Q (to be picked freely)
the diagonal must be 0's
the matrix must be symmetrical.
It is not strictly necessary for the matrix to be random (both random and non-random solutions are interesting, however), so for Q even, simply making each row a circular shift of the vector
[0 1 1 0 ... 0 0 0 ... 0 1 1] (for Q=4)
is a valid solution.
However, how to do this for Q odd? Or how to do it for Q even, but in a random fashion?
For those curious, I'm trying to test some phenomena on abstract networks.
I apologize if this has already been answered before, but none of the questions I could find had the symmetric restriction, which seems to make it much more complicated. I don't have a proof that such a matrix always exists, but I do assume so.
The object that you're trying to construct is known more canonically as an undirected d-regular graph (where d = Q). By the handshaking theorem, N and Q cannot both be odd. If Q is even, then connect vertex v to v + k modulo N for k in {-Q/2, -Q/2 + 1, ..., -1, 1, ..., Q/2 - 1, Q/2}. If Q is odd, then N is even. Construct a (Q - 1)-regular graph as before and then add connections from v to v + N/2 modulo N.
If you want randomness, there's a Markov chain whose limiting distribution is uniform on d-regular graphs. You start with any d-regular graph. Repeatedly pick vertices v, w, x, y at random. Whenever the induced subgraph looks like
v----w
x----y ,
flip it to
v w
| |
x y .
You can perhaps always follow your circular shift algorithm, when possible.
The only condition you need to follow while using the circular shift algorithm is to maintain the symmetric nature in the first row.
i.e. keeping Q 1's in the first row so that Q[0,1] to Q[0,N-1] {Assuming 0 indexed rows and cols, Q[0,0] is 0.} is symmetric, a simple example being 110010011.
Hence, N = 10, Q = 5, you can get many possible arrangements such as:
0 1 0 0 1 1 1 0 0 1
1 0 1 0 0 1 1 1 0 0
0 1 0 1 0 0 1 1 1 0
0 0 1 0 1 0 0 1 1 1
1 0 0 1 0 1 0 0 1 1
1 1 0 0 1 0 1 0 0 1
1 1 1 0 0 1 0 1 0 0
0 1 1 1 0 0 1 0 1 0
0 0 1 1 1 0 0 1 0 1
1 0 0 1 1 1 0 0 1 0
or
0 1 1 0 0 1 0 0 1 1
1 0 1 1 0 0 1 0 0 1
1 1 0 1 1 0 0 1 0 0
0 1 1 0 1 1 0 0 1 0
0 0 1 1 0 1 1 0 0 1
1 0 0 1 1 0 1 1 0 0
0 1 0 0 1 1 0 1 1 0
0 0 1 0 0 1 1 0 1 1
1 0 0 1 0 0 1 1 0 1
1 1 0 0 1 0 0 1 1 0
But as you can see for odd N(that means even N-1) and odd Q there can't be any such symmetric distribution.. Hope it helped.

How can I find a solution of binary matrix equation AX = B?

Given an m*n binary matrix A, m*p binary matrix B, where n > m what is an efficient algorithm to compute X such that AX=B?
For example:
A =
1 1 0 0 1 1 0 1 0 0
1 1 0 0 1 0 1 0 0 1
0 1 1 0 1 0 1 0 1 0
1 1 1 1 1 0 0 1 1 0
0 1 1 0 1 0 1 1 1 0
B =
0 1 0 1 1 0 1 1 0 1 0 0 1 0
0 0 1 0 1 1 0 0 0 1 0 1 0 0
0 1 1 0 0 0 1 1 0 0 1 1 0 0
0 0 1 1 1 1 0 0 0 1 1 0 0 0
1 0 0 1 0 0 1 0 1 0 0 1 1 0
Note, when I say binary matrix I mean matrix defined over the field Z_2, that is, where all arithmetic is mod 2.
If it is of any interest, this is a problem I am facing in generating suitable matrices for a random error correction code.
You can do it with row reduction: Place B to the right of A, and then swap rows (in the whole thing) to get a 1 in row 0, col 0; then xor that row to any other row that has a '1' in column 0, so you have only a single 1 in column 0. Then move to the next column; if [1,1] is zero then swap row 1 with a later row that has a 1 there, then xor rows to make it the only 1 in the column. Assuming 'A' is a square matrix and a solution exists, then you eventually have converted A to unity, and B is replaced with the solution to Ax=B.
If n > m, you have a system with more unknowns than equations, so you can solve for some of the unknowns, and set the others to zero. During the row reduction, if there are no values in a column which have a '1' to use (below the rows already reduced) you can skip that column and make the corresponding unknown zero (you can do this at most n-m times).

Resources