0
printf("\nNow its time to make a custom array. Please enter the number of rows: ");
int rows = scanf_s("%d", &rows);
printf("Now enter the number of columns: ");
int cols = scanf_s("%d", &cols);

int **custom2d;

custom2d = malloc(sizeof(int) * rows);

for (int i = 0; i < rows; i++)
{
    *(custom2d + i) = malloc(sizeof(int) * cols);
}

for (int i = 0; i < rows; i++)
{
    for (int j = 0; j < cols; j++)
    {
        printf("Enter value for [%d][%d]: ", i, j);
        scanf_s("%d", custom2d[i][j]);
    }
}

I am very new to C but I know several other higher level languages. I can't understand why this code isn't working. When I get to the prompt for entering the array value at the index, I get an exception(access violation writing location). I am very confused. All I'm trying to do is allow the user to specify rows, columns, and then input a value at each location of the array.

  • 5
    `int **` is not a 2D array, nor can it point to one. It is a completely different construct. – too honest for this site Apr 24 '17 at 10:54
  • Ok so I tried this before. Whenever I enter the first value at the first index, the console window just closes. – Eric Booker Apr 24 '17 at 10:56
  • @EricBooker Have you made both the correction xing suggested ? – ameyCU Apr 24 '17 at 10:59
  • 1
    The best way to ensure you're allocating the _correct_ type/size is to write `ptr_var = malloc(num * sizeof *ptr_var)`, in your case that would be `custom2d = malloc(rows *sizeof *custom2d);` and `custom2d[i] = malloc(cols * sizeof *custom2d[i]);`. – Elias Van Ootegem Apr 24 '17 at 10:59
  • Yeah I made both changes. The console window just closes after I enter the first value at [0][0]. This doesn't make any since as it should prompt for entry at each index. – Eric Booker Apr 24 '17 at 11:00
  • 1
    Consider learning to use a debugger to trace through the program line by line inspecting the values of the relevant variables to learn what is *really* going on. – alk Apr 24 '17 at 11:02
  • 4
    `int rows = scanf_s("%d", &rows);` → `int rows; scanf_s("%d", &rows);`, `int cols = scanf_s("%d", &cols);` → `int cols; scanf_s("%d", &cols);`. `scanf` returns the number of items successfully matched and assigned, not the input value. – Spikatrix Apr 24 '17 at 11:03
  • 2
    @CoolGuy: This catch should make all of us bow our heads in shame ... ;-} – alk Apr 24 '17 at 11:04
  • 1
    It seems the C provides you alot of ways to shoot yourself in the foot :O. I'm already intimidated of this language. – Eric Booker Apr 24 '17 at 11:05
  • 1
    "*several other higher level languages*" C isn't really "high" level .. – alk Apr 24 '17 at 11:06
  • I meant that I come from Python and C#. Grammar failure on my part. I know C is much closer to the hardware. – Eric Booker Apr 24 '17 at 11:08
  • @alk [Actually, it is](https://softwareengineering.stackexchange.com/q/267583) although I'd say it is one of the lower high level languages – Spikatrix Apr 24 '17 at 11:09
  • Cool Guy, the problem is solved. Thank you for preventing another face plant on my desk. – Eric Booker Apr 24 '17 at 11:10
  • Consider allocating a 2D array instead, it comes with a lot of benefits over your look-up table version. See [Correctly allocating multi-dimensional arrays](http://stackoverflow.com/questions/42094465/correctly-allocating-multi-dimensional-arrays) – Lundin Apr 24 '17 at 11:47

2 Answers2

3

Change this part :

int **custom2d;

custom2d = malloc(sizeof(int) * rows);

for (int i = 0; i < rows; i++)
{
    *(custom2d + i) = malloc(sizeof(int) * cols);
}

to :

int **custom2d;
custom2d = malloc(sizeof(int*) * rows);
if (custom2d == NULL)
{ 
    printf ("Error");
    return;
}
for (int i = 0; i < rows; i++)
{
    *(custom2d + i) = malloc(sizeof(int) * cols);
    if (custom2d[i] == NULL)
    {
        printf ("Error");
        return;
    }
}

See this link on why you should check the result of malloc. Also change :

scanf_s("%d", custom2d[i][j]);

to :

scanf_s("%d", &custom2d[i][j]);

Finally change :

int rows = scanf_s("%d", &rows);

and

int cols = scanf_s("%d", &cols);

to :

int rows;
scanf_s("%d", &rows);

and

int cols;
scanf_s("%d", &cols);

respectively, as right now you are using the return value of scanf_s and not the values read.

Community
  • 1
  • 1
Marievi
  • 4,951
  • 1
  • 16
  • 33
1

You need to allocate an array of pointers (int *) instead of int

custom2d = malloc(sizeof(int *) * rows); 

and then for more readability, imho, you can also do:

custom2d[i] = malloc(sizeof(int) * cols);

in both cases you should check if the allocation has been done:

   if (custom2d == NULL)
        printf ("No allocation made");

and

   if (custom2d[i] == NULL)
        printf ("No allocation made");

Moreover you need to pass the pointer to scanf_s:

scanf_s("%d", &custom2d[i][j]);

UPDATE

You need to change also this because scanf_s returns the number of fields successfully converted and assigned

int rows;
scanf_s("%d", &rows);

int cols;
scanf_s("%d", &cols);
granmirupa
  • 2,780
  • 16
  • 27