CapCity
7/11/2008 12:32:00 PM
"Walter Roberson" <roberson@ibd.nrc-cnrc.gc.ca> wrote in message
news:g55tgs$j63$1@canopus.cc.umanitoba.ca...
> In article <wxudk.77$8M.48@fe181.usenetserver.com>,
> CapCity <Cap@City.com> wrote:
>>#include <stdio.h>
>>#include <stdlib.h>
>>#include "ArrayManagement.h"
>>#include "Test.h"
>>
>>void MakeIVector(int *iv, int n1) {
>> int i;
>> iv = iVector(n1);
>
> iv is a pointer, so presumably iVector(n1) is allocating memory
> and returning the address of that memory, then to be stored into iv
>
>> for (i = 0; i < n1; i++) iv[i] = i*2;
>> for (i = 0; i < n1; i++) printf("%i\n", iv[i]);
>> return;
>
> An initial value for iv was passed in to MakeIVector but
> the new value (the address returned by iVector()) is not being
> passed out of the routine. Thus the calling routine has no idea
> where the allocated memory is.
>>}
>
>>int main() {
>> int n1 = 8;
>> int i, j, k;
>>
>> int* iv = iVector(n1);
>> for (i = 0; i < n1; i++) iv[i] = i;
>> for (i = 0; i < n1; i++) printf("%i\n", iv[i]);
>> Free_iVector(iv);
>> printf("\n");
>
>> int *iv2;
>> MakeIVector(iv2, n1);
>
> You have not initialized iv2, but you are passing its value into
> MakeIVector
>
>> printf("\n");
>> for (i = 0; i < n1; i++) iv2[i] = i;
>> for (i = 0; i < n1; i++) printf("%i\n", iv2[i]);
>>
>> exit(0);
>>}
>
>
> Your fundamental problem is that you are expecting that if a routine
> changes the value of a parameter that has been passed in, then the
> change will also be made in the calling routine. That is never the case in
> C.
> Any value passed in to a C routine is a *copy* of the value, and
> changes to the copy never affect the original.
>
> There are two basic solutions:
>
> 1) change MakeIVector so that it does not take iv as an input
> but returns the *pointer* iv as an output; or
>
> 2) Instead of passing in the -value- of (the uninitialized) iv2,
> pass in the -address- of that pointer (making the appropriate
> adjustment to the type of the parameter), and write the pointer
> through that address:
>
> void MakeIVector(int **iv, int n1) {
> int i;
> *iv = iVector(n1);
>
> for (i = 0; i < n1; i++) (*iv)[i] = i*2;
> for (i = 0; i < n1; i++) printf("%i\n", (*iv)[i]);
> return;
> }
>
> then later
>
> int *iv2;
> MakeIVector(&iv2, n1);
>
> After which the value of iv2 will have been changed to be the pointer
> to the allocated area.
>
> (There are other improvements possible to the program, such as using
> size_t instead of int for the sizes, in case the user wants to
> allocate more than 32767 int's.)
Thanks, Walter (and to the rest). That straightened things out for me.
I was aware (to a point) of the pass "by value" as opposed to "by
reference". To have a function change the value of an int or double you pass
in a pointer to the int or double.
But I needed to abstract that concept out a level for the one dimensional
array - I needed the function to change the value of a *pointer* so I needed
to pass in a pointer to the pointer. I was only providing the pointer
itself, thinking that was sufficient.
Thanks for getting me back on track.
> --
> "Whenever there is a hard job to be done I assign it to a lazy
> man; he is sure to find an easy way of doing it."
> -- Walter Chrysler