Again on passing arrays as arguments

M

Morgan

Thanks to all of you because I solved the problem related with my
previous post.
I simply made confusion with pointers to pointers and then succeeded
passing the reference to the first element pointer.
:))
You were right about by mixed code: quickly writing an example to
clarify the matter I made a C++ program, sorry for the inconvenience.

Anyway, although it all works fine with monodimensional arrays,
I still have a problem with irregular matrices (2D arrays with the
first dimension fixed, the second one variable).

I wrote a simple example code which perfectly works in the main
routine, while it arises an access violation if I put it in a
subroutine.
My purpose is to create an irregular matrix like this:

p[0][0] (no element)
p[1][0] p[1][1]

The two code blocks (in "main" and in "test") are identical, just
"p" changes in "*m".
The example is below.

Could you explain me why this occurs ?

Thanx again,
Morgan.
_________________________________________________________________
int main(int argc, char *argv[])
{
int **p;

p = (int **)malloc(2*sizeof(int *));
if (p == NULL) {printf("Error: Out of Memory \n"); exit(1);}
p[0] = (int *)malloc(sizeof(int));
if (p[0] == NULL) {printf("Error: Out of Memory \n"); exit(1);}
p[1] = (int *)malloc(2*sizeof(int));
if (p[1] == NULL) {printf("Error: Out of Memory \n"); exit(1);}

p[0][0] = 1; printf("%d\n",p[0][0]);
p[1][0] = 2; printf("%d\n",p[1][0]);
// Next line is normally executed here !!!!!!!!!!!!!!!!!!!
p[1][1] = 3; printf("%d\n",p[1][1]);

free(p);

test(&p);

printf("%d\n",p[0][0]);
printf("%d\n",p[1][0]);
printf("%d\n",p[1][1]);

free(p);

system("PAUSE");
return 0;
}

void test(int ***m)
{
*m = (int **)malloc(2*sizeof(int *));
if (*m == NULL) {printf("Error: Out of Memory \n"); exit(1);}
*m[0] = (int *)malloc(sizeof(int));
if (*m[0] == NULL) {printf("Error: Out of Memory \n"); exit(1);}
*m[1] = (int *)malloc(2*sizeof(int));
if (*m[1] == NULL) {printf("Error: Out of Memory \n"); exit(1);}

*m[0][0] = 1;
*m[1][0] = 2;
// Next line causes an access violation here !!!!!!!!!!!!!!!!!!!
*m[1][1] = 3;
// For the exactness it seems to me that the access violation
// arises after the last line, coming back to main... :-( !?
}
____________________________HELP !!!_____________________________
 
J

Josh Sebastian

Thanks to all of you because I solved the problem related with my
previous post.
I simply made confusion with pointers to pointers and then succeeded
passing the reference to the first element pointer.
:))
You were right about by mixed code: quickly writing an example to
clarify the matter I made a C++ program, sorry for the inconvenience.

If it's a C++ program, why'd you cross-post to comp.lang.c? The code below
looks an awful lot like C, so I'm kind of confused. Also, in acllc-c++, we
ask that you prefix your subject line with either [C] or [C++] so we can
easily tell which language you're using.
Anyway, although it all works fine with monodimensional arrays, I still
have a problem with irregular matrices (2D arrays with the first
dimension fixed, the second one variable).

I wrote a simple example code which perfectly works in the main routine,
while it arises an access violation if I put it in a subroutine. My
purpose is to create an irregular matrix like this:

p[0][0] (no element)
p[1][0] p[1][1]

The two code blocks (in "main" and in "test") are identical, just "p"
changes in "*m".
The example is below.

Could you explain me why this occurs ?

Thanx again,
Morgan.
_________________________________________________________________ int
main(int argc, char *argv[])

You're not using argc or argv. If you don't use them, leave them out.
{
int **p;

p = (int **)malloc(2*sizeof(int *));

In C, don't cast the return from malloc; it gains you nothing, and it can
hide bugs (which it did in this case). In C++, use `new' instead. If you
use malloc said:
if (p == NULL) {printf("Error: Out of Memory \n"); exit(1);}

You need <stdio.h> (or <cstdio> in C++) for printf. 1 is a non-portable
exit code. The only portable codes are 0 (indicates success),
EXIT_SUCCESS, and EXIT_FAILURE.
p[0] = (int *)malloc(sizeof(int));
if (p[0] == NULL) {printf("Error: Out of Memory \n"); exit(1);}
p[1] = (int *)malloc(2*sizeof(int));
if (p[1] == NULL) {printf("Error: Out of Memory \n"); exit(1);}

Please you more vertical space. It's your friend, really. Until you become
much more familiar with the language, one statement per line is a good
rule of thumb.
p[0][0] = 1; printf("%d\n",p[0][0]);
p[1][0] = 2; printf("%d\n",p[1][0]);
// Next line is normally executed here !!!!!!!!!!!!!!!!!!!

It took me a while to figure out what you meant by that comment. I don't
know if you're a native English speaker or not, but you meant, "Next line
is executed normally here." Inverting the order of those two words changes
the meaning drastically.
p[1][1] = 3; printf("%d\n",p[1][1]);

free(p);

Memory leak: you forgot to free() p[0] and p[1] first.
test(&p);

printf("%d\n",p[0][0]);
printf("%d\n",p[1][0]);
printf("%d\n",p[1][1]);

free(p);

system("PAUSE");
return 0;
}

void test(int ***m)
{
*m = (int **)malloc(2*sizeof(int *));
if (*m == NULL) {printf("Error: Out of Memory \n"); exit(1);}
*m[0] = (int *)malloc(sizeof(int));
if (*m[0] == NULL) {printf("Error: Out of Memory \n"); exit(1);}
*m[1] = (int *)malloc(2*sizeof(int));
if (*m[1] == NULL) {printf("Error: Out of Memory \n"); exit(1);}

You've got duplicated code here. Why not call test() twice instead of
having cut-and-pasted code?
*m[0][0] = 1;
*m[1][0] = 2;
// Next line causes an access violation here !!!!!!!!!!!!!!!!!!!
*m[1][1] = 3;
// For the exactness it seems to me that the access violation // arises
after the last line, coming back to main... :-( !?

You've got the order of operator precedence wrong. You meant

(*m)[0][0] = 1;
(*m)[1][0] = 2;
(*m)[1][1] = 3;
}
____________________________HELP !!!_____________________________

Josh
 
J

Jumbo

Morgan said:
Thanks to all of you because I solved the problem related with my
previous post.
I simply made confusion with pointers to pointers and then succeeded
passing the reference to the first element pointer.
:))
You were right about by mixed code: quickly writing an example to
clarify the matter I made a C++ program, sorry for the inconvenience.
I am reading this in alt.comp.learn.c-c++ and it looks like you have also
posted this to comp.lang.c.
The people in comp.lang.c won't be happy if your posting C++ code to their
newsgroup.
Anyway, although it all works fine with monodimensional arrays,
I still have a problem with irregular matrices (2D arrays with the
first dimension fixed, the second one variable).

I wrote a simple example code which perfectly works in the main
routine, while it arises an access violation if I put it in a
subroutine.
My purpose is to create an irregular matrix like this:

p[0][0] (no element)
p[1][0] p[1][1]

The two code blocks (in "main" and in "test") are identical, just
"p" changes in "*m".
The example is below.

Could you explain me why this occurs ?

Thanx again,
Morgan.
_________________________________________________________________
int main(int argc, char *argv[])
{
int **p;

p = (int **)malloc(2*sizeof(int *));
if (p == NULL) {printf("Error: Out of Memory \n"); exit(1);}
p[0] = (int *)malloc(sizeof(int));
if (p[0] == NULL) {printf("Error: Out of Memory \n"); exit(1);}
p[1] = (int *)malloc(2*sizeof(int));
if (p[1] == NULL) {printf("Error: Out of Memory \n"); exit(1);}

p[0][0] = 1; printf("%d\n",p[0][0]);
p[1][0] = 2; printf("%d\n",p[1][0]);
// Next line is normally executed here !!!!!!!!!!!!!!!!!!!
p[1][1] = 3; printf("%d\n",p[1][1]);

free(p);

test(&p);

printf("%d\n",p[0][0]);
printf("%d\n",p[1][0]);
printf("%d\n",p[1][1]);

free(p);

system("PAUSE");
return 0;
}

void test(int ***m)
{
*m = (int **)malloc(2*sizeof(int *));
if (*m == NULL) {printf("Error: Out of Memory \n"); exit(1);}
*m[0] = (int *)malloc(sizeof(int));
if (*m[0] == NULL) {printf("Error: Out of Memory \n"); exit(1);}
*m[1] = (int *)malloc(2*sizeof(int));
if (*m[1] == NULL) {printf("Error: Out of Memory \n"); exit(1);}

*m[0][0] = 1;
*m[1][0] = 2;
// Next line causes an access violation here !!!!!!!!!!!!!!!!!!!
*m[1][1] = 3;
// For the exactness it seems to me that the access violation
// arises after the last line, coming back to main... :-( !?
}
____________________________HELP !!!_____________________________

First decide if your writing C code or C++ code.

If your writing C++ code try something like this:

#include <iostream>

/* function declaration & definition */
void foo(int** p){
std::cout<< "p[0][0] = " << p[0][0] << '\n' ;
std::cout<< "p[1][1] = " << p[1][1] << '\n' ;
p[0][1] = 21;
p[1][0] = 31;
}
/* simply prints two values and alters two */


int main(){
/** establish some values for dimensions **/
unsigned int DIM1 =2;
unsigned int DIM2 =2;

/** create array **/
int** ArrayIdent = new int*[DIM1];
for(unsigned int i=0; i<DIM1; ++i)
ArrayIdent = new int[DIM2];

/** assign some values **/
ArrayIdent[0][0] = 1;
ArrayIdent[0][1] = 2;
ArrayIdent[1][0] = 3;
ArrayIdent[1][1] = 4;

/** pass to function **/
foo(ArrayIdent);

/** print a couple of values **/
std::cout<< "ArrayIdent[0][1] = " << ArrayIdent[0][1] << '\n' ;
std::cout<< "ArrayIdent[1][0] = " << ArrayIdent[1][0] << '\n' ;

/** free memory **/
for(unsigned int i=0; i<DIM1; ++i)
delete [] ArrayIdent;
delete [] ArrayIdent;

return 0;
}


I know it's logical to think of an extra level of indirection to pass the
address of a pointer but you don't need it here, simply pass the array
identifier by value(as this is the address* of the array).

*virtual address or whatever type of addressing your system uses. Should be
fine in most cases but I believe there are some systems out there which use
varaible sized pointers and caution should be exercised in this case when
passing any pointer. (i.e passing 32-bit pointers to 64-bit routines and
vice versa).
HTH.
 

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,755
Messages
2,569,537
Members
45,022
Latest member
MaybelleMa

Latest Threads

Top