-2

I have a rather large program that requires me to use pointers to 2 dimensional arrays. I'm having a difficult time allocating space for the arrays.

I've already tried allocating the space at the time of declaration but I ran into a million road blocks.

I found code here: Create a pointer to two-dimensional array

I have a 2D array of pointers to an array other_arrays

I have this:

    static double other_arrays[51][1];
    double (*SumH)[51][1] = &other_arrays;
    double (*WeightIH)[51][1] = &other_arrays;
    double (*Hidden)[51][1] = &other_arrays;
    double (*SumO)[51][1] = &other_arrays;
    double (*WeightHO)[51][1] = &other_arrays;
    double (*Output)[51][1] = &other_arrays;
    double (*DeltaWeightIH)[51][1] = &other_arrays;
    double (*DeltaWeightHO)[51][1] = &other_arrays;
    for (i = 0; i < 2; i++){
      for (j = 0; j < 51; j++){
        SumH[j][i] = (double *)malloc(sizeof(double));
        WeightIH[j][i] = (double *)malloc(sizeof(double));
        Hidden[j][i] = (double *)malloc(sizeof(double));
        SumO[j][i] = (double *)malloc(sizeof(double));
        WeightHO[j][i] = (double *)malloc(sizeof(double));
        Output[j][i] = (double *)malloc(sizeof(double));
        DeltaWeightIH[j][i] = (double *)malloc(sizeof(double));
        DeltaWeightHO[j][i] = (double *)malloc(sizeof(double));
      }
    }

When I compile I get: error: array type 'double [1]' is not assignable

I've tried some things I've found online such as SumH[j] = (double *)malloc(sizeof(double));

But then I get: error: array type 'double [51][1]' is not assignable

Or something like this yields the same error:

  for (j = 0; j < 51; j++){
    SumH[j] = (double *)malloc(sizeof(double));
    WeightIH[j] = (double *)malloc(sizeof(double));
    Hidden[j] = (double *)malloc(sizeof(double));
    SumO[j] = (double *)malloc(sizeof(double));
    WeightHO[j] = (double *)malloc(sizeof(double));
    Output[j] = (double *)malloc(sizeof(double));
    DeltaWeightIH[j] = (double *)malloc(sizeof(double));
    DeltaWeightHO[j] = (double *)malloc(sizeof(double));
  }

SOLUTION

I didn't cast malloc

    *SumH[j][i] = *(double *)malloc(sizeof(double));
Community
  • 1
  • 1
  • 1
    Do not cast `malloc()` to the target type. – Iharob Al Asimi Jan 14 '16 at 00:27
  • @iharob I'm getting a bus error at a 3D allocation `*Input[i][j][k] = *(double *)malloc(sizeof(double));` i = 20 j = 2 k = 51 – kendall weihe Jan 14 '16 at 00:36
  • 2
    @iharob This is probably the most cited sentence for c-tagged questions at SO. However, common sense is that it is a matter of style. Insisting that it is a Bad Thing[tm] to cast the return value of malloc() is a bit too dogmatic in my eyes. – Ctx Jan 14 '16 at 00:36
  • Are you trying to end up with an array of pointers or a pointer to an array? – user253751 Jan 14 '16 at 00:36
  • @iharob am I running out of memory? – kendall weihe Jan 14 '16 at 00:36
  • @iharob I guess I'm overflowing, but I'm not going past the bounds of the array of pointers – kendall weihe Jan 14 '16 at 00:39
  • @immibis array of pointers – kendall weihe Jan 14 '16 at 00:40
  • @kendallweihe You should think about an array of size one. The only useful thing would be if you need to pass it as a parameter sometimes, in this case it seems pointless. – Iharob Al Asimi Jan 14 '16 at 00:41
  • 1
    your outer loop range is 0-1, but your second dimension is 1 not 2. Why is it 1, BTW? – Bob__ Jan 14 '16 at 00:47
  • Suggestion: this isn't really an MCVE ([How to create a Minimal, Complete, and Verifiable Example?](http://stackoverflow.com/help/mcve)). You have the same problem 8 times in a row. Two of the arrays would be sufficient to demonstrate your problem. I'm trying to work out the significance of the multiple initializations with `&other_arrays`. Since all 8 arrays are pointing at the same space, the first 7 arrays worth of allocations are being leaked as the assignments for the last array overwrites the others, doesn't it? – Jonathan Leffler Jan 14 '16 at 00:54

2 Answers2

1

If you want to allocate 2d arrays:

    /* allocate 2d arrays */
    double (*SumH)[51][1] = malloc(51*1*sizeof(double));
    double (*WeightIH)[51][1] = malloc(51*1*sizeof(double));
    double (*Hidden)[51][1] = malloc(51*1*sizeof(double));
    double (*SumO)[51][1] = malloc(51*1*sizeof(double));
    double (*WeightHO)[51][1] = malloc(51*1*sizeof(double));
    double (*Output)[51][1] = malloc(51*1*sizeof(double));
    double (*DeltaWeightIH)[51][1] = malloc(51*1*sizeof(double));
    double (*DeltaWeightHO)[51][1] = malloc(51*1*sizeof(double));
    /* ... */
    free(DeltaWeightHO);
    free(DeltaWeightIH);
    free(Output);
    free(WeightHO);
    free(SumO);
    free(Hidden);
    free(WeightIH);
    free(SumH);

Usage would be ... (*SumH)[j][i] ...

I doubt this is want you wanted. To allocate pointers to the first row of 2d arrays:

    /* allocate pointers to first row of 2d arrays */
    double (*SumH)[1] = malloc(51*1*sizeof(double));
    double (*WeightIH)[1] = malloc(51*1*sizeof(double));
    double (*Hidden)[1] = malloc(51*1*sizeof(double));
    double (*SumO)[1] = malloc(51*1*sizeof(double));
    double (*WeightHO)[1] = malloc(51*1*sizeof(double));
    double (*Output)[1] = malloc(51*1*sizeof(double));
    double (*DeltaWeightIH)[1] = malloc(51*1*sizeof(double));
    double (*DeltaWeightHO)[1] = malloc(51*1*sizeof(double));

Usage would be ... SumH[j][i] ...

To allocate array of pointers to rows

    /* allocate array of pointers to rows */
    double (*SumH[51])[1];
    for(i = 0; i < sizeof(SumH)/sizeof(SumH[0]); i++)
        SumH[i] = malloc(1*sizeof(double));

Usage would be ... SumH[j][i] ...

rcgldr
  • 27,407
  • 3
  • 36
  • 61
1

If you want pointers to arrays and want to initialize them, then you should be doing things much more simply:

double (*SumH)[5][2] = malloc(sizeof(*SumH));
double (*WeightIH)[5][2] = malloc(sizeof(*WeightIH));

Now you can use:

int k = 0;
for (int i = 0; i < 5; i++)
{
    for (int j = 0; j < 2; j++)
    {
        (*SumH)[i][j] = k;
        (*WeightIH)[i][j] = k++;
    }
}

Note that an array dimension of [1] is close to pointless.

FWIW, valgrind gives the following code a clean bill of health:

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

int main(void)
{
    double (*SumH)[5][2] = malloc(sizeof(*SumH));
    double (*WeightIH)[5][2] = malloc(sizeof(*WeightIH));


    int k = 0;
    for (int i = 0; i < 5; i++)
    {
    for (int j = 0; j < 2; j++)
    {
        (*SumH)[i][j] = k;
        (*WeightIH)[i][j] = k++;
    }
    }

    for (int i = 0; i < 5; i++)
    {
    for (int j = 0; j < 2; j++)
        printf("[%f, %f]", (*SumH)[i][j], (*WeightIH)[i][j]);
    putchar('\n');
    }

    free(SumH);
    free(WeightIH);

    return 0;
}

The output is not very exciting:

[0.000000, 0.000000][1.000000, 1.000000]
[2.000000, 2.000000][3.000000, 3.000000]
[4.000000, 4.000000][5.000000, 5.000000]
[6.000000, 6.000000][7.000000, 7.000000]
[8.000000, 8.000000][9.000000, 9.000000]
Jonathan Leffler
  • 730,956
  • 141
  • 904
  • 1,278