-1

So I'm trying to find diagonals on a grid. I've tried looking at some stack overflow pages that seemed to provide a clue but most of them includes itertools or numpy and a lot of built in functions.

Note: U may have seen this question somewhere else. This is basically @Bruffff's second account

So I'm just asking on behalf of all the beginners here, what's the most basic way to find all the diagonals in a given grid.

Here is what I have so far:

def columns(test):
    ans = []
    for x, lst in enumerate(test):
        if x < len(test)-1:
           ans.append(lst[x+1])
    return ans
print(columns(test))

and given this grid,

test = [["r","a","w","b","i","t"],
        ["x","a","y","z","c","h"],
        ["p","q","b","e","i","e"],
        ["t","r","s","b","o","g"],
        ["u","w","x","v","i","t"]
        ["u","w","x","v","i","t"],

the output returns

['a', 'y', 'e', 'o', 't']

but my expected output is

[(u), (uw) (twx), (prxv), (xqsvi), (rabbit), (ayeot), (wzig), (bce),(ih), (t)]

How can I do this without using the complex built in functions and import, numpy or itertools??

I know they may be easier, but I want to learn things using the basics first, so yea, please use the most basic of approaches to do this. Thank you:)

Dave Shah
  • 91
  • 6
  • traverse from -rows, 0 and 0 to coloumn and get the lower diagnoal and then 0-row and 0-col to get upper triagnle coloumn, ie change the grid size – sahasrara62 Nov 09 '21 at 08:32
  • yo, thank u for ur response but can u give like examples of what do u mean lol. I dont rlly understand what u said sorry – Dave Shah Nov 09 '21 at 08:36
  • Unorthodox method, but you can add 6 nulls either side of each row and get the six-long diagonals from there. (And remove the nulls/whitespace using `.strip()`) – Larry the Llama Nov 09 '21 at 08:54
  • 1
    Why do you ask the same question again, if you already have [several answers](https://stackoverflow.com/q/69869205/5472354) the first time around? – mapf Nov 09 '21 at 08:56
  • 1
    Does this answer your question? [How can I make my code simpler and still get the same output?](https://stackoverflow.com/questions/69869205/how-can-i-make-my-code-simpler-and-still-get-the-same-output) – mapf Nov 09 '21 at 08:56
  • This question has already answered here: https://stackoverflow.com/questions/23069388/listing-elements-in-a-nested-lists-diagonally – s.ouchene Nov 09 '21 at 08:57

3 Answers3

0
def Diagonals(test):
    l = len(test)
    temp = [] # Add whitespaces to end
    result = []
    for row in test:
        temp.append([" "]*(l-1)+row+[" "]*(l-1))
    test = temp
    for i in range(l):
        current = ""
        for j in range(2*l-1):
            current += test[i+j][j]
        result.append(current.strip())
    return result

What this code is doing is adding whitespaces onto the end of the list, so that it can just get all (6) length diagonals, then trims off the whitespaces at the end.

i.e. for 3

*.bob..
.*obo..
..*ob..

.*bob..
..*bo..
..b*b..

..*ob..
..o*o..
..bo*..

..b*b..
..ob*..
..bob*.

..bo*..
..obo*.
..bob.*
Larry the Llama
  • 958
  • 3
  • 13
0

Here you go, but it isn't ordered though!

   def columns(test):
      results = set()
      for i in range(len(test)):
        tmp1=""
        tmp2=""
        for j in range(0,len(test)-i):
            tmp1+=test[i+j][j]
            tmp2+=test[j][i+j]
        results.add(tmp1)
        results.add(tmp2)
      return list(results) # if you need to return it like a list

Returned value:

['ih', 'prxv', 'u', 't', 'bce', 'twx', 'rabbit', 'ayeot', 'wzig', 'uw', 'xqsvi']

Edit:

for "other diagonal side":

def columns(test):
    results = set()
    n=len(test)
    for i in range(n):
        tmp1=""
        tmp2=""
        for j in range(i+1):
            tmp1+=test[i-j][j]
            tmp2+=test[n-1-j][n-1-i+j]
        results.add(tmp1)
        results.add(tmp2)
    return list(results)
  • hey thank u for ur response. What if I want to find like the other diagonal side. Like should I change -i in 'for j"?? – Dave Shah Nov 09 '21 at 09:23
  • thank u again. One last question, if we want to print like from bottom to top instead of top to bottom like what u did, for each of the columns, can we do reversed(list(results))? – Dave Shah Nov 09 '21 at 10:50
0

a very long and not so efficient implementation

# your code goes here
def get_row_from_grid(l):
    """ take 2D matrix and give, diagonal elements"""

    return "".join([v2 for i, v in enumerate(l) for j, v2 in enumerate(v) if i == j])




l = [      ["r", "a", "w", "b", "i", "t"],
            ["x", "a", "y", "z", "c", "h"],
            ["p", "q", "b", "e", "i", "e"],
            ["t", "r", "s", "b", "o", "g"],
            ["u", "w", "x", "v", "i", "t"],
            ["u", "w", "x", "v", "i", "t"]]

val1, val2 = len(l)-1, 0
result = []

# traversing lower triangular matrix
for i in range(len(l)-1, -1, -1):
        tmp = get_row_from_grid([j[:len(l)-i] for j in l[i:]])
        result.append(tmp)

#  traversing upper triangluar matrix
for i in range(0, len(l)):
    tmp = get_row_from_grid( [ j[i+1:] for j in  l[:][i:]])
    if tmp:
        result.append(tmp)
print(result)

output

['u', 'uw', 'twx', 'prxv', 'xqsvi', 'rabbit', 'ayeot', 'yeot', 'eot', 'ot', 't']
sahasrara62
  • 10,069
  • 3
  • 29
  • 44