Moving through each element of a (potentially non square) 2d array, diagonally

Viewed 131

I was playing around with 2d arrays in c, and I am wondering how to traverse a 2d array, fully and diagonally.

Horizontally, in the matrix of dimensions width,height you can just move through each index i, and inspect elements at index j

Something like:

const int width = 10;
const int height = 10;
const int mat[width][height] = {0};
for (i = 0, i<width, i++){
     for (j = 0; j<height; j++){
         mat[i][0] = j;
     }
}

I just added in something random so the loop did something..., however, the key is that I was traversing in the correct direction

vertically would be similar, with some flipped parameters

however diagonally...I am a bit lost; I cannot think of a way to traverse in a diagonal way. Conceptually I may want to hit the 4x3 matrix in the following order:

 1  2  4  7
 3  5  8 10
 6  9 11 12

Or with indices i,j :

0,0 -> 
1,0 -> 0,1 -> 
2,0 -> 1,1 -> 0,2 -> 
2,1 -> 1,2 -> 0,3 ->
2,2 -> 1,3 ->
2,3

Is there a straightforward way to hit these elements(not necessarily in that order per say, but I think it would be useful to increment diagonally)

Also, is it possible to check the diagonals in the opposite direction ?

2 Answers

For diagonal traverse, use only one for loop, as both i and j are identical:

for (i = 0, i < min(width, hight), i++){
    // something to do with element[i][i]
}

This is a duplicate of Traverse Matrix in diagonal strips where is it suggested something like :

int main(void)
{
    int m[3][4] = { 1, 2, 4, 7,
                    3, 5, 8,10,
                    6, 9,11,12 };

    const int h = 3; /* height*/
    const int w = 4; /* width */
    for (int diag = 0; diag < (w + h - 1); ++diag)
    {
        printf("diag %d:",diag);
        int i_start = diag < w ? 0 : diag - w + 1;
        int i_end = diag < h ? diag + 1 : h;
        for (int i = i_start; i < i_end; ++i)
        {
            printf("%d ",m[i][diag - i]);
        }
        printf("\n");
    }
    return 0;
}

Output:

diag 0:1
diag 1:2 3
diag 2:4 5 6
diag 3:7 8 9
diag 4:10 11
diag 5:12
Related