dynamic 2 D array with malloc??

V

VijaKhara

hi all,

i am trying to create a dynamic 2D array with size N x 3 (N will be
put in as a parameter) using the following code:

int **xyz;
int i,N;

N=30000;
xyz=malloc(3*sizeof(int*));
for (i=0; i<N;i++)
xyz=malloc(sizeof(int)*N);


the program ran too slow and finally error appeared when i increased
to 6288:
"Unhandled exception in proj1.exe :0xC0000005:Access violation.

it seems a "run out off memory error" . my pc has 600Mb RAM and around
1Gb free in harddisk.

Iam wondering if my array is too large that my pc's RAM can't handle?
it is amazing.

plz help??
 
C

Chris Dollin

i am trying to create a dynamic 2D array with size N x 3 (N will be
put in as a parameter) using the following code:

int **xyz;
int i,N;

N=30000;
xyz=malloc(3*sizeof(int*));
for (i=0; i<N;i++)

Um. Shouldn't that N be 3?
xyz=malloc(sizeof(int)*N);


Yes, it should. BOOM today.

PS usual remarks about preferred style of mallocation.
 
N

Nick Keighley

i am trying to create a dynamic 2D array with size N x 3 (N will be
put in as a parameter) using the following code:

int **xyz;
int i,N;

by convention uppercase is reserved for macros.

N=30000;
xyz=malloc(3*sizeof(int*));

since 3 is fixed you could do

int *xyz[3];

if you use malloc() then test the return value

for (i=0; i<N;i++)
xyz=malloc(sizeof(int)*N);


um. You allocate 3 int*s then you try to index 30,000 items in
this block of memory.

You meant:

for (i = 0; i < 3; i++)
{
xyz = malloc(sizeof (int) * N);
if (xyz[0] == NULL)
handle_error();
}

note how judicious use of whitespace imprves readability.

the program ran too slow and finally error appeared when i increased
to 6288:
"Unhandled exception in proj1.exe :0xC0000005:Access violation.

it seems a "run out off memory error" . my pc has 600Mb RAM and around
1Gb free in harddisk.

Iam wondering if my array is too large that my pc's RAM can't handle?
it is amazing.

just because your PC has 600M doesn't mean the OS will let you have it
all.

try this

p = malloc(3 * N * sizeof(int*));

if (p == NULL)
printf ("can't malloc that!!\n);
 
R

Richard Heathfield

Malcolm McLean said:
N is an exception. There is a strong convention for using N to hold a
count.

That's the first I've heard of such a convention. When did that happen?
 
J

Joe Wright

hi all,

i am trying to create a dynamic 2D array with size N x 3 (N will be
put in as a parameter) using the following code:

int **xyz;
int i,N;

N=30000;
xyz=malloc(3*sizeof(int*));
for (i=0; i<N;i++)
xyz=malloc(sizeof(int)*N);


the program ran too slow and finally error appeared when i increased
to 6288:
"Unhandled exception in proj1.exe :0xC0000005:Access violation.

it seems a "run out off memory error" . my pc has 600Mb RAM and around
1Gb free in harddisk.

Iam wondering if my array is too large that my pc's RAM can't handle?
it is amazing.

plz help??

You are not programming the problem. Three rows of 30,000 ints should be
doable like this..

int **xyz;
int i, r = 3, c = 30000;

xyz = malloc(r * sizeof *xyz);
for (i = 0; i < r; ++i)
xyz = malloc(c * sizeof **xyz);

What do you think?
 
B

Ben Pfaff

Malcolm McLean said:
N is an exception. There is a strong convention for using N to hold a count.

Really? What base of code is it that makes use of this
convention? I have not encountered it, and I think of myself as
someone who has read a lot of code.
 
R

Richard Heathfield

Joe Wright said:

int **xyz;
int i, r = 3, c = 30000;

xyz = malloc(r * sizeof *xyz);
for (i = 0; i < r; ++i)
xyz = malloc(c * sizeof **xyz);

What do you think?


I think xyz could be NULL at the point where you deref it. Why, what do
/you/ think? :)
 
R

Richard Tobin

N is an exception. There is a strong convention for using N to hold a
count.
[/QUOTE]
That's the first I've heard of such a convention. When did that happen?

In my experience it's much more often lowercase. But it raises a good
point: conventions often conflict. If you're using C to implement
some published algorithm there's no particular reason why C's
conventions should trump the algorithm's. You just have to judge
which will be most convenient for readers and maintainers of the
code.

-- Richard
 
O

Old Wolf

N is an exception. There is a strong convention for using N to hold a count.

I've never seen it. I do use lower case 'n' for a count in
throwaway code, but never upper case.
 
F

Flash Gordon

Richard Tobin wrote, On 15/03/07 22:27:
That's the first I've heard of such a convention. When did that happen?

In my experience it's much more often lowercase. But it raises a good
point: conventions often conflict. If you're using C to implement
some published algorithm there's no particular reason why C's
conventions should trump the algorithm's. You just have to judge
which will be most convenient for readers and maintainers of the
code.[/QUOTE]

Unless the convention of the algorithm uses both 'N' and 'n' I would say
that the case conventions of C should be used. After all, someone
reading the code who knows the algorithm is unlikely to be confused by a
change of case, and if they know C as well they are likely to know the C
conventions as well and so expect it.
 
R

Richard Tobin

In my experience it's much more often lowercase. But it raises a good
point: conventions often conflict. If you're using C to implement
some published algorithm there's no particular reason why C's
conventions should trump the algorithm's. You just have to judge
which will be most convenient for readers and maintainers of the
code.
[/QUOTE]
Unless the convention of the algorithm uses both 'N' and 'n'

.... that's just the case I was thinking of. But there are also
conventions like vectors being in capitals where you might want to use
case to distinguish even when there is no name clash.

-- Richard
 
F

Flash Gordon

Richard Tobin wrote, On 16/03/07 01:19:
Unless the convention of the algorithm uses both 'N' and 'n'

... that's just the case I was thinking of.[/QUOTE]

I would say the algorithm uses a horrible convention in that case, one
that makes it harder to talk (as opposed to write) about it. Talking you
would have to keep saying "capital N", "lower case n" and the like.
> But there are also
conventions like vectors being in capitals where you might want to use
case to distinguish even when there is no name clash.

If the distinction is not obvious from the name then I would add vect_
to the start of the names. I still do not see it confusing someone
familiar enough with the algorithm to know the conventions it uses, and
someone not familiar with the algorithm but familiar with C will find it
easier.
 
R

Richard Tobin

... that's just the case I was thinking of.
[/QUOTE]
I would say the algorithm uses a horrible convention in that case, one
that makes it harder to talk (as opposed to write) about it. Talking you
would have to keep saying "capital N", "lower case n" and the like.

Mathematicians (and physicists etc) are used to this. They generally
say "big N" and "little n".

-- Richard
 
V

VijaKhara

Thank you very much. I have fixed the problem/ Now I am confused how
to free this 2D array:


If my code is as follows:

int **xyz;
int i, r = 3, c = 30000;


xyz = malloc(r * sizeof(*int));
for (i = 0; i < r; ++i)
xyz = malloc(c * sizeof **xyz);

how to free this memory block:

for (i=0;i<r;i++)
free xyz;

does it work?

and one more question what is difference between :

for (i = 0; i < r; ++i)

and

for (i = 0; i < r; i++)

I often use the later.

Thanks



I would say the algorithm uses a horrible convention in that case, one
that makes it harder to talk (as opposed to write) about it. Talking you
would have to keep saying "capital N", "lower case n" and the like.

Mathematicians (and physicists etc) are used to this. They generally
say "big N" and "little n".

-- Richard[/QUOTE]
 
C

Chris Dollin

and one more question what is difference between :

for (i = 0; i < r; ++i)

and

for (i = 0; i < r; i++)

There's no visible difference. (Since the value of `++i` or
`i++` is never accessed, the fact that they're different doesn't
make any difference.)
I often use the later.

I use `i += 1`; as a general rule, I use the ++ forms when the
value is used, and the += form when it isn't.

(Yes, I know that the += form has a value.)
 
F

Flash Gordon

Richard Tobin wrote, On 16/03/07 16:01:
I would say the algorithm uses a horrible convention in that case, one
that makes it harder to talk (as opposed to write) about it. Talking you
would have to keep saying "capital N", "lower case n" and the like.

Mathematicians (and physicists etc) are used to this. They generally
say "big N" and "little n".[/QUOTE]

Doesn't mean it isn't horrible and doesn't make it harder ;-)
 
U

user923005

From the C-FAQ:

6.16: How can I dynamically allocate a multidimensional array?

A: The traditional solution is to allocate an array of pointers,
and then initialize each pointer to a dynamically-allocated
"row." Here is a two-dimensional example:

#include <stdlib.h>

int **array1 = malloc(nrows * sizeof(int *));
for(i = 0; i < nrows; i++)
array1 = malloc(ncolumns * sizeof(int));

(In real code, of course, all of malloc's return values would
be checked.)

You can keep the array's contents contiguous, at the cost of
making later reallocation of individual rows more difficult,
with a bit of explicit pointer arithmetic:

int **array2 = malloc(nrows * sizeof(int *));
array2[0] = malloc(nrows * ncolumns * sizeof(int));
for(i = 1; i < nrows; i++)
array2 = array2[0] + i * ncolumns;

In either case, the elements of the dynamic array can be
accessed with normal-looking array subscripts: arrayx[j]
(for 0 <= i < nrows and 0 <= j < ncolumns).

If the double indirection implied by the above schemes is for
some reason unacceptable, you can simulate a two-dimensional
array with a single, dynamically-allocated one-dimensional
array:

int *array3 = malloc(nrows * ncolumns * sizeof(int));

However, you must now perform subscript calculations manually,
accessing the i,jth element with array3[i * ncolumns + j]. (A
macro could hide the explicit calculation, but invoking it would
require parentheses and commas which wouldn't look exactly like
multidimensional array syntax, and the macro would need access
to at least one of the dimensions, as well. See also question
6.19.)

Yet another option is to use pointers to arrays:

int (*array4)[NCOLUMNS] = malloc(nrows * sizeof(*array4));

but the syntax starts getting horrific and at most one dimension
may be specified at run time.

With all of these techniques, you may of course need to remember
to free the arrays (which may take several steps; see question
7.23) when they are no longer needed, and you cannot necessarily
intermix dynamically-allocated arrays with conventional,
statically-allocated ones (see question 6.20, and also question
6.18).

Finally, in C9X you can use a variable-length array.

All of these techniques can also be extended to three or more
dimensions.

References: C9X Sec. 6.5.5.2.
 
C

CBFalconer

Thank you very much. I have fixed the problem/ Now I am confused
how to free this 2D array: If my code is as follows:

int **xyz;
int i, r = 3, c = 30000;

xyz = malloc(r * sizeof(*int));
for (i = 0; i < r; ++i)
xyz = malloc(c * sizeof **xyz);

how to free this memory block:

for (i=0;i<r;i++)
free xyz;

does it work?


Please don't top-post. Your answer belongs after, or intermixed
with, the snipped material which you quote.

No, it doesn't work. You have to reverse all the malloc actions.
So the appropriate code would be:

for (i = 0; i < r; i++) free xyz;
free(xyz);
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,769
Messages
2,569,580
Members
45,055
Latest member
SlimSparkKetoACVReview

Latest Threads

Top