Pass matrix as pointer

Asked

Viewed 9,758 times

5

I need to make the proposal:

Elaborate a function that takes as parameters a pointer of an array, the number of rows and columns, and print the matrix elements.

But I am learning pointers and having difficulties, I have tried in several ways to pass the pointer of the matrix but anyway it gives error. Now the error is on the line:

            printf("\t%d",*mtr[lin][col]);
[Error] invalid types 'int* (*)[4][int*]' for array subscript

Here is my code:

#include <stdio.h>
#include <stdlib.h>

int matriz_ponteiro(int *mtr[3][4], int *lin, int *col){
    // imprimir a matriz
    for (*lin=0; *lin<3; *lin++){
        printf("\n");
        for (*col=0; *col<4; *col++){
            printf("\t%d",*mtr[lin][col]);
        }   
    }
    return *mtr[lin][col];

}


int main (){
    int res, mtr [3][4];
    int lin, col, cont;
    cont = 0;
    // armazenar o valor de cont em cada posição da matriz
    for (lin=0; lin<3; lin++){
        for (col=0; col<4; col++){
            mtr[lin][col]= cont++;
        }
    }
    res = matriz_ponteiro(mtr[3][4], lin, col);
}
  • 1

    Is there a reason to use these pointers? They are not necessary.

  • Yes, no pointer was very easy... But the exercise statement asks the function to receive as parameters a pointer of an matrix :(

2 answers

5

I understand the code - first alternative

Look at that line:

matriz_ponteiro(mtr[3][4], lin, col);

lin and col are of the type int. mtr is a 3x4 matrix of the type int, and therefore mtr[3] is an array of 4 positions of the type int and finally mtr[3][4] is a int. That is, the three parameters you pass are ints.

In defining function, we have this:

int matriz_ponteiro(int *mtr[3][4], int *lin, int *col){

That is, the parameters are of the types "pointer to 3x4 matrix of int", "pointer to int" and "pointer to int". That is, they don’t match what you use to call more down.

Well, in your code you mix matrices, pointers and integers more or less randomly, which shows that you shouldn’t know what you’re doing, so let’s take it easy. Apparently, the purpose of its function matriz_ponteiro is to print the matrix. So here’s its header:

void matriz_ponteiro(int mtr[3][4])

Why? Because it receives a 3x4 array of integers to print (int mtr[3][4] and returns no result (void).

No parameters are required lin and col because it will go through all the rows and columns. So the implementation is like this:

void matriz_ponteiro(int mtr[3][4]) {
    int lin, col;
    for (lin = 0; lin < 3; lin++) {
        printf("\n");
        for (col = 0; col < 4; col++) {
            printf("\t%d", mtr[lin][col]);
        }
    }
}

And with that, in your main, instead:

res = matriz_ponteiro(mtr[3][4], lin, col);

Use this:

matriz_ponteiro(mtr);

And you can also delete the variable res.

Here’s your complete code:

#include <stdio.h>
#include <stdlib.h>

void matriz_ponteiro(int mtr[3][4]) {
    int lin, col;
    for (lin = 0; lin < 3; lin++) {
        printf("\n");
        for (col = 0; col < 4; col++) {
            printf("\t%d", mtr[lin][col]);
        }
    }
}

int main() {
    int mtr[3][4];
    int lin, col, cont;
    cont = 0;
    // armazenar o valor de cont em cada posição da matriz
    for (lin = 0; lin < 3; lin++) {
        for (col = 0; col < 4; col++) {
            mtr[lin][col]= cont++;
        }

    }
    matriz_ponteiro(mtr);
}

See here working on ideone.

Second alternative

If you have to have the number of rows and columns as parameter, you can do this:

#include <stdio.h>
#include <stdlib.h>

void matriz_ponteiro(int linhas, int colunas, int matriz[linhas][colunas]) {
    int lin, col;
    for (lin = 0; lin < linhas; lin++) {
        for (col = 0; col < colunas; col++) {
            printf("\t%d", matriz[lin][col]);
        }
        printf("\n");
    }
}

int main() {
    int mtr[3][4];
    int lin, col, cont;
    cont = 0;
    // armazenar o valor de cont em cada posição da matriz
    for (lin = 0; lin < 3; lin++) {
        for (col = 0; col < 4; col++) {
            mtr[lin][col] = cont++;
        }
    }
    matriz_ponteiro(3, 4, mtr);
}

See here working on ideone. It is important to note that the matrix has to be the last parameter, as its definition depends on the number of rows and columns that have to be declared before (i.e., in the previous parameters).

The matrix used there is a pointer. To prove this, try placing at the end of the function matriz_ponteiro, that:

    mtr[0][0] = 1234;

And at the end of main, use this twice:

    matriz_ponteiro(3, 4, mtr);

And you’ll notice that the matrix is actually altered from within the matriz_ponteiro. If it were only copied, 1234 would not appear when calling the function matriz_ponteiro again. This is only possible because a reference passage has occurred, not just values. And if there was a reference pass in C, it’s because there was a pointer pass.

Third alternative

However, if you want the function matriz_ponteiro receive an explicit pointer, so you can do so:

#include <stdio.h>
#include <stdlib.h>

void matriz_ponteiro(int *matriz, int linhas, int colunas) {
    int lin, col;
    for (lin = 0; lin < linhas; lin++) {
        if (lin != 0) printf("\n");
        for (col = 0; col < colunas; col++) {
            printf("\t%d", matriz[lin * colunas + col]);
        }
    }
}

int main() {
    int mtr[3][4];
    int lin, col, cont;
    cont = 0;
    // armazenar o valor de cont em cada posição da matriz
    for (lin = 0; lin < 3; lin++) {
        for (col = 0; col < 4; col++) {
            mtr[lin][col] = cont++;
        }

    }
    matriz_ponteiro(mtr[0], 3, 4);
}

See it working on ideone.

That one matriz[lin * colunas + col] needs a better explanation. What happens is that the elements of the matrix are placed in the form of one line after the other. That is, the matrix consists of a sequence of rows and each row has a number of elements equal to the number of columns. This can also be interpreted as an array with linhas * colunas elements. Such a formula lin * colunas + col accesses the desired element if you are using this form of indexing.

The use of mtr[0] in the end it’s because the guy has to be a int *, and not a int **. Another way would be to cast an explicit cast as well (use (int *) mtr).

  • Thanks for the explanations, but Celso said unfortunately the statement asks the function to receive as a parameter a pointer of a matrix. What your full code doesn’t solve. Without pointer I can do tbm, the problem is I still don’t quite understand the use of pointers.

  • @ADR Response edited. Good now?

  • Yes, that’s exactly what I wanted to do. Thank you very much :)

2


This whole code doesn’t make much sense and at various points it doesn’t do what you think it does. It can be simplified, organized and modernized like this, there it works:

#include <stdio.h>
#include <stdlib.h>

void matriz_ponteiro(int mtr[3][4]) {
     for (int lin = 0; lin < 3; lin++) {
        for (int col = 0; col < 4; col++) printf("\t%d", mtr[lin][col]);
        printf("\n");
    }
}

int main () {
    int mtr[3][4];
    for (int lin = 0, cont = 0; lin < 3; lin++) for (int col = 0; col < 4; col++) mtr[lin][col] = cont++;
    matriz_ponteiro(mtr);
}

Behold working in the ideone. And in the repl it.. Also put on the Github for future reference.

It may be that there was some other goal, but this is not clear in the question, what you can infer is there. If you have specific questions you can do. Learning to program in trial and error is not the most productive way, nor does it usually work very well.

Using pointers:

#include <stdio.h>
#include <stdlib.h>
#define LINHA 3
#define COLUNA 4

void matriz_ponteiro(int **mtr, size_t linhas, size_t colunas) {
     for (int lin = 0; lin < linhas; lin++) {
        for (int col = 0; col < colunas; col++) printf("\t%d", mtr[lin][col]);
  
        printf("\n");
    }
}

int main () {
    int **mtr = malloc(LINHA * sizeof(*mtr));
    for (int lin = 0, cont = 0; lin < LINHA; lin++) {
        mtr[lin] = malloc(COLUNA * sizeof(*mtr[lin]));
        for (int col = 0; col < COLUNA; col++) mtr[lin][col] = cont++;
    }
    matriz_ponteiro(mtr, LINHA, COLUNA);
}

Behold working in the ideone. And in the repl it.. Also put on the Github for future reference.

  • Yes, this way it works, but you are not using pointers... And the proposed exercise asks : Elaborate a function that receives as parameters a pointer of an array, the number of rows and columns, and print the matrix elements

  • The problem is that it doesn’t make sense.

  • @ADR did totally with pointers.

  • I saw it here, but it’s giving error on the line: int mtr = malloc(LINE * sizeof(mtr)); [Error] invalid Conversion from 'void' to 'int' [-fpermissive] For you gave no error?

  • @ADR you clicked on links what I have provided? See that it is working?

  • Sure, there it works. Obg!!

Show 1 more comment

Browser other questions tagged

You are not signed in. Login or sign up in order to post.