Author |
Message |
Gora #1 / 17
|
using malloc to allocate a 2-D array
I'm having problems trying to dynamicallly allocate memory for an array of 2-dimensions. I started the following: /*********************\ int **arr1; int x,y; x=4; y=4; arr1 = malloc(x * y * sizeof(int)); /*****************\ but this doesn't allocate an array big enough. I want to be able to refer to the array elements by using eg. arr[1][2] I think you have to first allocate mem for the whole array and then loop through allocations for the individual pointers? Can anybody help;
|
Sun, 03 Apr 2005 15:13:41 GMT |
|
|
Joona I Palast #2 / 17
|
using malloc to allocate a 2-D array
Quote: > I'm having problems trying to dynamicallly allocate memory for an > array of 2-dimensions. > I started the following: > /*********************\ > int **arr1; > int x,y; > x=4; > y=4; > arr1 = malloc(x * y * sizeof(int)); > /*****************\ > but this doesn't allocate an array big enough. > I want to be able to refer to the array elements by using eg. > arr[1][2] > I think you have to first allocate mem for the whole array and then > loop through allocations for the individual pointers? > Can anybody help;
Yes, that is right. If you want to allocate a 2D array then you have to first allocate memory for the pointers to 1D arrays, and then you have to allocate those 1D arrays separately. --
| Kingpriest of "The Flying Lemon Tree" G++ FR FW+ M- #108 D+ ADA N+++| | http://www.helsinki.fi/~palaste W++ B OP+ | \----------------------------------------- Finland rules! ------------/ "You could take his life and..." - Mirja Tolsa
|
Sun, 03 Apr 2005 15:30:57 GMT |
|
|
nrk #3 / 17
|
using malloc to allocate a 2-D array
Quote:
> I'm having problems trying to dynamicallly allocate memory for an > array of 2-dimensions. > I started the following: > /*********************\ > int **arr1; > int x,y; > x=4; > y=4; > arr1 = malloc(x * y * sizeof(int)); > /*****************\ > but this doesn't allocate an array big enough. > I want to be able to refer to the array elements by using eg. > arr[1][2] > I think you have to first allocate mem for the whole array and then > loop through allocations for the individual pointers? > Can anybody help;
Please read the fine FAQ for this group. Specifically 6.16 (http://www.eskimo.com/~scs/C-faq/q6.16.html) which addresses precisely this issue. -nrk. ps: Is anyone else bothered by the fact that this comes under arrays and pointers while there is a separate section called Memory allocation (Perhaps there is some reference to this question inside that section that I have missed)?
|
Sun, 03 Apr 2005 15:59:44 GMT |
|
|
Dave Near #4 / 17
|
using malloc to allocate a 2-D array
On 16 Oct 2002 00:13:41 -0700, Goran said: Quote: > I'm having problems trying to dynamicallly allocate memory for an > array of 2-dimensions.
This is a FAQ - 6.16 (I think maybe it should be in section 7? Possibly just a stub question with a reference to the answer in section 6?). Quote: > int **arr1; > int x,y; > x=4; > y=4; > arr1 = malloc(x * y * sizeof(int));
arr1 is of type int** so you'll want to allocate space for a number of int *s rather than ints to it. And you'll probably want that number to be the number of rows So... arr1 = malloc(x * sizeof(int *)); Now you need to allocate space for the next level of indirection (the int *s to the ints). You want x*y ints, and they should start being stored at arr1[0][0], assuming you want array-type contiguousness. arr1[0] = malloc(x * y * sizeof(int)); And now all that's left to do is point all the other arr1[i]s to the right place in that contiguous block of memory - for (i = 1; i < x; i++) arr1[i] = arr1[0] + i * y; Quote: > but this doesn't allocate an array big enough.
It does, but you have not done what you need to do to reference it correctly. You now have an x*y block of ints lying about, with x int *s pointing at appropriate spots in there, and 1 int ** pointing to the first int *. Quote: > I want to be able to refer to the array elements by using eg. > arr[1][2] > I think you have to first allocate mem for the whole array and then > loop through allocations for the individual pointers?
Something like that. The FAQ answer, and the bits above (which are more or less verbatim from the FAQ), should help. Cheers, Dave. -- David Neary, E-Mail: bolsh at gimp dot org CV: http://www.redbrick.dcu.ie/~bolsh/CV/CV.html
|
Sun, 03 Apr 2005 16:34:13 GMT |
|
|
CBFalcone #5 / 17
|
using malloc to allocate a 2-D array
Quote:
> I'm having problems trying to dynamicallly allocate memory for an > array of 2-dimensions. > I started the following: > /*********************\ > int **arr1; > int x,y; > x=4; > y=4; > arr1 = malloc(x * y * sizeof(int)); > /*****************\ > but this doesn't allocate an array big enough. > I want to be able to refer to the array elements by using eg. > arr[1][2] > I think you have to first allocate mem for the whole array and then > loop through allocations for the individual pointers?
You are not thinking clearly. Consider "int **arr1;" and rewrite it as "int* *arr1;". Now it is obvious that *arr1 is a pointer to a pointer to an integer. arr1 = malloc(x * y * sizeof(int)); ^^^^^^^^^^^^^^^^^^^ Now this has nothing to do with pointers to integers. It is getting a pointer to a block of memory sufficient to hold x*y integers, which you could remap as a two dimensional array of integers. i.e. the type of arr1 is wrong, it should be a pointer to integer. If you had replaced "sizeof(int)" with "sizeof(*arr1)" you would have gotten room for x * y pointers to integers, which is still not what you want. But if you had properly defined arr1 in the first place, as "int *arr1;" you would have had the right thing. A two dimensional array is a mapping of a one dimensional array of constant size. It can be simulated with a one dimensional array of pointers to other one dimensional arrays (which may remove the requirement for constant size). Both methods have advantages, depending on usage. --
Available for consulting/temporary embedded and systems. <http://cbfalconer.home.att.net> USE worldnet address!
|
Sun, 03 Apr 2005 19:03:47 GMT |
|
|
sellountos euripide #6 / 17
|
using malloc to allocate a 2-D array
Quote:
>I'm having problems trying to dynamicallly allocate memory for an >array of 2-dimensions. >I started the following: >/*********************\ >int **arr1; >int x,y; >x=4; >y=4; >arr1 = malloc(x * y * sizeof(int)); >/*****************\
<snip> Here's some code snippets for memory allocation. Any Error handling is ommited. i is declared as integer. if ((arr1=malloc(x*sizeof*arr1))==NULL) { /* Allocation failed. Error Handling*/ } for (i=0;i<x;i++) { if ((arr1[i]=malloc(y*sizeof*arr1[i]))==NULL) { /* Allocation failed. Error Handling*/ } } /* Do interesting things with arr1[i][j] where 0<=i<x and 0<=j<y */ /* Deallocate */ for (i=0;i<x;i++) { free(arr1[i]); } free(arr1); cheers #yuri#
|
Sun, 03 Apr 2005 19:33:00 GMT |
|
|
Nan-Shan Ch #7 / 17
|
using malloc to allocate a 2-D array
Quote:
>I'm having problems trying to dynamicallly allocate memory for an >array of 2-dimensions.
(snip) I think the others have answered your question. I'm dumping my matrix-allocation functions for your reference and for the other to critisize and improve/ debug. But, I've been using these for quite a long time without problems I can tell. (I'm using bounds-checkers.) The advantages of my approach is: * You are able to call routines written in different fasions -- either using two indices or addressing a 1-dimensional block. * Swapping two "scanline" (if it is an image) or "row" (if it is to be consider a matrix) is piece of pie and time-saving. You'll have to define REAL to whatever you like. For example: #define REAL int int **A; int m, n, i, j; .... A=matrix(m, n); .... for (i=0, i<m; i++) for (j=0; j<n; j++) (access A[i][j] ...) or int *iptr; pitr= &A[0][0]; for (i=0; i<m*n; i++) (access *iptr++ ... etc.) free_matrix(A); Two functions follow. regards Rudi -------------------------- REAL **matrix(int m, int n) /* the array starts at aa[0] */ { REAL *a, **aa; int i; /*** allocate a conticous block of m x n REAL ***/ a = malloc( sizeof(REAL) * m * n ); /* allocate data-block */ if ( NULL == a ) { fprintf(stderr, "*** %s/matrix()/%d: ", __FILE__, __LINE__); fprintf(stderr, "malloc() %ld REAL's failed\n", (long)m * (long)n); exit(EXIT_FAILURE); /* 941634627 */ } aa = malloc( sizeof(REAL*) * (m+1) ); /* allocate pointer-block */ if ( NULL == aa ) { fprintf(stderr, "*** %s/matrix()/%d: ", __FILE__, __LINE__); fprintf(stderr, "malloc() %d (REAL*)'s failed\n", m); exit(EXIT_FAILURE); /* 941634627 */ } aa[0] = a; /* a hidden copy of ptr to data-block for safety */ ++aa; /* because some functions swap row-ptr's instead of row-data */ for (i=0; i<m; i++) /* assign pointers to pointer-block */ { aa[i] = a + (i * n); } return aa; /* aa[0] = pointer to data-block ONLY IF it is not swapped */ Quote: }
void free_matrix(REAL **AA) { --AA; free( AA[0]); /* free data-block */ free( AA ); /* free pointer-block */ Quote: }
|
Sun, 03 Apr 2005 20:11:44 GMT |
|
|
Tak-Shing Cha #8 / 17
|
using malloc to allocate a 2-D array
Quote: > a = malloc( sizeof(REAL) * m * n ); /* allocate data-block */ > if ( NULL == a ) > { > fprintf(stderr, "*** %s/matrix()/%d: ", __FILE__, __LINE__); > fprintf(stderr, "malloc() %ld REAL's failed\n", (long)m * (long)n); > exit(EXIT_FAILURE); /* 941634627 */ > } > aa = malloc( sizeof(REAL*) * (m+1) ); /* allocate pointer-block */
This somehow reminds me of the infamous NR code: http://www.nr.com/pubdom/nrutil.c.txt <g,d&r> Tak-Shing
|
Sun, 03 Apr 2005 21:12:05 GMT |
|
|
Nan-Shan Ch #9 / 17
|
using malloc to allocate a 2-D array
Quote:
>> a = malloc( sizeof(REAL) * m * n ); /* allocate data-block */ >> if ( NULL == a ) >> { >> fprintf(stderr, "*** %s/matrix()/%d: ", __FILE__, __LINE__); >> fprintf(stderr, "malloc() %ld REAL's failed\n", (long)m * (long)n); >> exit(EXIT_FAILURE); /* 941634627 */ >> } >> aa = malloc( sizeof(REAL*) * (m+1) ); /* allocate pointer-block */ > This somehow reminds me of the infamous NR code: > http://www.nr.com/pubdom/nrutil.c.txt
Would you please point out specifically a problem in my codes? I think my pointers never point outside the areas I have allocated, no? I'm aware of the controversial NR-codes. The NR-codes use tricks for 1-offset matrices, while my functions use 0-offset that is native to C. One cannot even apply bounds-checkers to the NR-codes sometimes, while I'm using the bounds-checker by Richard W.M. Jones. Regards Rudi
|
Sun, 03 Apr 2005 21:20:11 GMT |
|
|
Tak-Shing Cha #10 / 17
|
using malloc to allocate a 2-D array
Quote: > Would you please point out specifically a problem in my codes? > I think my pointers never point outside the areas I have > allocated, no?
No, but there are a couple of other minor problems. A non-exhausive list of possible problems: (1) m*n could overflow (2) exit() is not a good way of handling errors if this code is to be reused by other people (3) malloc(sizeof(type)) is bad style (4) The ++aa hack is unnecessary (design issue) Tak-Shing
|
Sun, 03 Apr 2005 21:53:08 GMT |
|
|
Herbert Rosen #11 / 17
|
using malloc to allocate a 2-D array
Quote: > I'm having problems trying to dynamicallly allocate memory for an > array of 2-dimensions. > I started the following: > /*********************\
you declares a pointer to an pointer. Right, you can uses that as access base to an pointer array that contains pointers to values. Quote: > int **arr1; > int x,y; > x=4; > y=4;
int *arr1[][] or simply int *arr[]; where the former is better because it documents the usage better. Quote: >arr1 = malloc(x * y * sizeof(int));
you gets an address of an array of [4][4] but it seems you likes to get an array of pointers to arrays. int *arr1[] = malloc(x * sizeof(int*)) for (i = 0; i < y; i ++) { arr1[i] = malloc(y * sizeof(int)); Quote: } > /*****************\ > but this doesn't allocate an array big enough.
When your x or y axis is begger than 4 members you have to change the value, right. You gets exactly what you want. Quote: > I want to be able to refer to the array elements by using eg. > arr[1][2]
see above. Quote: > I think you have to first allocate mem for the whole array and then > loop through allocations for the individual pointers?
No, either you defines a pointer to an array of arrays, that is you allocates the memory as you've done, or you declares an array of pointers to arrays of <type> as the second way shows. If you really needs a matrix of 4 rows with 4 columns each then the first method shows better. If you needs an array with rows of variable lengh columns the second is better, even as you can use the second for fixed length. Quote: > Can anybody help;
-- Tschau/Bye Herbert Rosenau http://www.pc-rosenau.de eComStation Reseller in Germany
|
Sun, 03 Apr 2005 22:59:02 GMT |
|
|
Nan-Shan Ch #12 / 17
|
using malloc to allocate a 2-D array
Quote:
>> a = malloc( sizeof(REAL) * m * n ); /* allocate data-block */ >> if ( NULL == a ) >> { >> fprintf(stderr, "*** %s/matrix()/%d: ", __FILE__, __LINE__); >> fprintf(stderr, "malloc() %ld REAL's failed\n", (long)m * (long)n); >> exit(EXIT_FAILURE); /* 941634627 */ >> } >> aa = malloc( sizeof(REAL*) * (m+1) ); /* allocate pointer-block */ > A non-exhausive list of possible problems:
Thanks for checking in the first place. Quote: > (1) m*n could overflow > (3) malloc(sizeof(type)) is bad style
What about a = malloc( sizeof(REAL) * (size_t)m * n ); /* allocate data-block */ Is there still a danger of overflow? Please follow-up and this will be changed immediately in my codes. As for the style, sorry, I don't follow. What would you do for instance? I'm mostly varying between float and double in my codes using #define REAL float/double. Quote: > (2) exit() is not a good way of handling errors if this
code >is to be reused by other people Yes I agree here. I'm aware of that too. Somehow I have not changed it yet. A NULL for the caller is better without changing the prototype. What do you say? Quote: > (4) The ++aa hack is unnecessary (design issue)
I'll have to recall my intention of that design that time and reply later. Why do you call that a "hack"? Do you mean that degrades readability of the codes? Further critiques are welcome. (See my first post in this thread.) I've stopped learning new things in C a long time. Rudi
|
Sun, 03 Apr 2005 23:35:55 GMT |
|
|
Nan-Shan Ch #13 / 17
|
using malloc to allocate a 2-D array
Quote:
>> (4) The ++aa hack is unnecessary (design issue) >I'll have to recall my intention of that design that time >and reply later. Why do you call that a "hack"? Do you mean >that degrades readability of the codes?
I recall the reason of the design now. It is commented in my function matrix() and the advantages in my first post. So, it is necessary. Rudi
|
Sun, 03 Apr 2005 23:59:04 GMT |
|
|
Ben Pfaf #14 / 17
|
using malloc to allocate a 2-D array
Quote:
> /*********************\
Others have pointed out the problems that you're looking to solve, but I'd like to point out that you forgot to terminate your comment. Comments in C end with */, not with *\.
|
Mon, 04 Apr 2005 00:22:29 GMT |
|
|
Nan-Shan Ch #15 / 17
|
using malloc to allocate a 2-D array
Quote:
>> /*********************\ >Others have pointed out the problems that you're looking to >solve, but I'd like to point out that you forgot to terminate >your comment. Comments in C end with */, not with *\.
To the OP. I think this is no joke and you'll have to take that seriously. I've once looked for this typo (in my case /**** /) a whole day (if not more), until I got myself a syntax highlighted editor and found it. Rudi
|
Mon, 04 Apr 2005 00:33:05 GMT |
|
|