Passing 2-D Arrays of unknown size ?

Daniel E. Platt platt at ndla.UUCP
Sat Dec 23 02:46:21 AEST 1989


In article <3180 at uceng.UC.EDU>, mfinegan at uceng.UC.EDU (michael k finegan) writes:
> 
>     While I think the answer is no, I'll ask anyway! :-)
> 
>     Is there a method for passing/using multi-D arrays in subroutines,
> without specifying the column (fastest changing) dimension in advance ? No way
> to set the column length dynamically ? Any more elegant alternatives ?

Actually, there isn't a very 'clean' way using doubly indexed arrays (as your	code showed...), however, there is a way that looks transparant.  Consider
a dynamic allocation routine:


double **alloc_array(m, n)
int		m, n;
{
	int		i, j;
	double	**res;

	/* try to allocate collum pointers */
	if((res = (double **)malloc(m * sizeof(double *))) == NULL)
		/* couldn't allocate it */
		return NULL;

	/* try to allocate the rows for each column */
	for(i = 0; i < m; i++)
		if((res[i] = (double *)malloc(n * sizeof(double))) == NULL){
			/* couldn't do it; need to de-allocate everything */
			for(j = 0; j < i; j++)
				free(res[j]);
			free(res);
			return NULL;
	}

	/* Success!!! */
	return res;

}

Then, when you want to mess with an m X n array a, just declare

	double	**a;

	/* ... */

	if((a = alloc_array(m, n)) == NULL){
		fprintf(stderr, "Couldn't allocate \"a\".\n");
		exit(1);
	}

	/* ... */


Then, when you need to pass it to a function array_manipulate(), do it
like:

	array_manipulate(a, m, n);

and array_manipulate() is declared to look like:

void array_manipulate(a, m, n)
double	**a;
int	m, n;
{
	/* ... */

	a[i][j] = /* stuff... */

	/* ... */

}

Namely, the technique allows for transparant array passing of arbitrary
dimension.

Further, this technique has the advantage of working on non-rectangular arrays	(so, you want a triangular array? FINE!!! you want a tri-diagonal array? NO
PROBLEM!!! just name it! we can make it!!!).

Further, this has the advantage of being FAST!!  On some monte-carlo stuff that	required frequent array lookups, this outperformed some Fortran code by a 
factor of two (using Microsoft C vs. Fortran on PC's... this is an interesting
comparison because both compilers use the same 'back end').  I conjecture
this is because Fortran requires multiplication to find the correct displacement
through the array, whereas the above C code requires only table lookups.

Hope you find this fun and to your advantage!!

Dan Platt
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
||                                     1(914)945-1173            ||
||        Dan Platt                    1(914)941-2474            ||
||        Watson (IBM)                 PLATT at YKTVMV.BITNET       ||
||                           ..!uunet!bywater!scifi!ndla!platt   ||
||                                                               ||
||     The opinions expressed here do not necessarily reflect    ||
||                   those of my employer!                       ||
||                                                               ||
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-



More information about the Comp.lang.c mailing list