Home > Enterprise >  Given any odd sided square following this pattern, algorithmically create its matching list of lists
Given any odd sided square following this pattern, algorithmically create its matching list of lists

Time:12-16

The Pattern

You are given only the side length of a square:

  • The side length is ALWAYS = ODD.
  • The middle of the square's value ALWAYS = 0.
  • Every other value = distance from the center of the square.

Write a program that generalizes this algorithm and creates a list representation of the input square by outputting a List of Lists

Example Output

"""
if input = 1    
Matching square:        0         =>  List Equivalent = [[0]]

if input = 3
Matching square:      1 1 1       =>  List Equivalent = [[1, 1, 1],
                      1 0 1                              [1, 0, 1],
                      1 1 1                               [1, 1, 1]]

if input = 5
Matching square:    2 2 2 2 2     =>  List Equivalent = [[2, 2, 2, 2, 2],
                    2 1 1 1 2                            [2, 1, 1, 1, 2], 
                    2 1 0 1 2                            [2, 1, 0, 1, 2],
                    2 1 1 1 2                            [2, 1, 1, 1, 2],
                    2 2 2 2 2                            [2, 2, 2, 2, 2]]

if input = 7
Matching square:  3 3 3 3 3 3 3   =>  List Equivalent = [[3, 3, 3, 3, 3, 3, 3],
                  3 2 2 2 2 2 3                          [3, 2, 2, 2, 2, 2, 3],
                  3 2 1 1 1 2 3                          [3, 2, 1, 1, 1, 2, 3],
                  3 2 1 0 1 2 3                          [3, 2, 1, 0, 1, 2, 3],
                  3 2 1 1 1 2 3                          [3, 2, 1, 1, 1, 2, 3],
                  3 2 2 2 2 2 3                          [3, 2, 2, 2, 2, 2, 3],
                  3 3 3 3 3 3 3                          [3, 3, 3, 3, 3, 3, 3]]

"""

I'm tryin a solution that I will post that splits the square unevenly about 0 like so:

side = 5                                       _ _ _ _ _ _
Matching square:    2 2 2 2 2     Split square: 2 1 0 1 2
                    2 1 1 1 2                   2 1 1 1 2
                    2 1 0 1 2                   2 2 2 2 2        
                    2 1 1 1 2                           
                    2 2 2 2 2 

And figure out how to generate each row based on its distance from the top row etc

Question

Any existing solutions to this kind of pattern / problem that I'm trying to solve? I do not know what to search

CodePudding user response:

One relatively easy but not elegant way to do it is to spiral the matrix from the outside to the inside and decrement the value for each new cycle. As follows:

def create_matrix(n): 
   curr = n // 2 
   matrix = [[0]*n for _ in range(n)] 
    
   counter = 0 
   N = n*n 
   left, right, top, bottom = 0, n-1, 0, n-1 
   while True: 
       # top 
       for i in range(left, right 1): 
           matrix[top][i] = curr 
           counter  = 1 
       top  = 1 
       if counter >= N: 
           break 
       # right 
       for i in range(top, bottom 1): 
           matrix[i][right] = curr 
           counter  = 1 
       right -= 1 
       if counter >= N: 
           break 
       # bottom 
       for i in range(left, right 1): 
           matrix[bottom][i] = curr 
           counter  = 1 
       bottom -= 1 
       if counter >= N: 
           break 
       # left 
       for i in range(top, bottom 1): 
           matrix[i][left] = curr 
           counter  = 1 
       left  = 1 
       if counter >= N: 
           break 
       curr -= 1 
   return matrix

A quick test:

In [2]: create_matrix(11)                                                                                              
Out[2]: 
[[5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5],
 [5, 4, 4, 4, 4, 4, 4, 4, 4, 4, 5],
 [5, 4, 3, 3, 3, 3, 3, 3, 3, 4, 5],
 [5, 4, 3, 2, 2, 2, 2, 2, 3, 4, 5],
 [5, 4, 3, 2, 1, 1, 1, 2, 3, 4, 5],
 [5, 4, 3, 2, 1, 0, 1, 2, 3, 4, 5],
 [5, 4, 3, 2, 1, 1, 1, 2, 3, 4, 5],
 [5, 4, 3, 2, 2, 2, 2, 2, 3, 4, 5],
 [5, 4, 3, 3, 3, 3, 3, 3, 3, 4, 5],
 [5, 4, 4, 4, 4, 4, 4, 4, 4, 4, 5],
 [5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5]]

In [3]: create_matrix(5)                                                                                               
Out[3]: 
[[2, 2, 2, 2, 2],
 [2, 1, 1, 1, 2],
 [2, 1, 0, 1, 2],
 [2, 1, 1, 1, 2],
 [2, 2, 2, 2, 2]]

CodePudding user response:

Solved in a much simpler way

square_size = 11
centre_x = (square_size - 1) // 2
centre_y = (square_size - 1) // 2

matrix = []
for x in range(square_size):
    row = []
    for y in range(square_size):
        x_dif = abs(x - centre_x)
        y_dif = abs(y - centre_y)
        value = max(x_dif, y_dif)
        row.append(value)
    matrix.append(row)
  • Related