Module 2 3 Passing pointers PASS BY VALUE

Module 2 -3: Passing pointers

PASS BY VALUE (CASE 1) – Pass a simple variable by value. #include <stdio. h> #include <stdlib. h> %p is the code for printing a Hexadecimal integer with a ‘ 0 x’ prefix added. We need this as we are printing the ‘address of I’ (&I). void FOO(int I) { printf("FOO: %d %pn", I, &I); I = 42; printf("FOO: %d %pn", I, &I); } FOO: 55 0 xb 3 e 9 b 8 dc FOO: 42 0 xb 3 e 9 b 8 dc Note how the change to I (I=42) in FOO is not returned to main where I is still 55. int main(void) { int I; I = 55; printf("MAIN: %d %pn", I, &I); FOO(I); printf("MAIN: %d %pn", I, &I); return 0; } MAIN: 55 0 xb 3 e 9 b 904 Note we are printing the value of I and the address of I. The address of I in FOO is different from the address of I in main. This tells us that the I in FOO is a copy of the I in main.

PASS BY VALUE (CASE 2) - Pass a variable(referenced by a pointer) by value. #include <stdio. h> #include <stdlib. h> void FOO(int I) { printf("FOO: %d %pn", I, &I); I = 42; printf("FOO: %d %pn", I, &I); } Note that I is a pointer. FOO: 99 0 xb 3 e 9 b 8 dc FOO: 42 0 xb 3 e 9 b 8 dc Note how the change to I (I=42) in FOO is not returned to main where I is still 99. int main(void) { int *I; I = (int*)calloc(1, sizeof(int)); *I = 99; printf("MAIN: %d %pn", *I, &(*I)); printf("MAIN: %d %pn", *I, I); FOO(*I); printf("MAIN: %d %pn", *I, I); return 0; } The address of I in FOO is different from the address of I in main. This tells us that the I in FOO is a copy of the I in main. MAIN: 99 0 xae 2010 Note that I and &(*I) do the same thing. Dereferencing I to get its value.

PASS BY REFERENCE (CASE 1) –Pass a simple variable by reference. #include <stdio. h> #include <stdlib. h> void BAR(int *I) { printf("BAR: %d %pn", *I, &(*I)); *I = 42; printf("BAR: %d %pn", *I, &(*I)); } BAR: 55 0 xb 3 e 9 b 904 BAR: 42 0 xb 3 e 9 b 904 Note how the change to I (I=42) in BAR is returned to main. int main(void) { int I; I = 55; printf("MAIN: %d %pn", I, &I); BAR(&I); printf("MAIN: %d %pn", I, &I); printf("n"); return 0; } The address of I. MAIN: 55 0 xb 3 e 9 b 904 MAIN: 42 0 xb 3 e 9 b 904 The address of I in BAR and I in main is the same. This tells us that they are in fact the same variable (refer to the same memory location).

PASS BY REFERENCE (CASE 2) –Pass a variable (referenced by a pointer) by reference. #include <stdio. h> #include <stdlib. h> void BAR(int *I) { printf("BAR: %d %pn", *I, &(*I)); *I = 42; printf("BAR: %d %pn", *I, &(*I)); } Note that I is a pointer. BAR: 99 0 xae 2010 BAR: 42 0 xae 2010 The address of I in BAR and I in main is the same. This tells us that they are in fact the same variable (refer to the same memory location). Note how the change to I (I=42) in BAR is returned to main. int main(void) { int *I; I = (int*)calloc(1, sizeof(int)); *I = 99; printf("MAIN: %d %pn", *I, I); BAR(I); printf("MAIN: %d %pn", *I, I); printf("n"); return 0; } MAIN: 99 0 xae 2010 MAIN: 42 0 xae 2010 Since I is a pointer, the name of the pointer gives us the address of the pointer.

PASS BY REFERENCE (CASE 3) – Pass a pointer (referenced by a pointer) by reference. #include <stdio. h> #include <stdlib. h> void FOOBAR(int *(*I)) { printf("FOOBAR: %d %pn", *(*I), *I); *I = (int*)calloc(1, sizeof(int)); *(*I) = 42; printf("FOOBAR: %d %pn", *(*I), *I); } We need to make sure the compiler understands that we do not want a 2 -d array (**), so we use the notation *(*) to force the compiler to understand this is a pointer passed by reference. FOOBAR: 99 0 xae 2030 FOOBAR: 42 0 xae 2050 Note that I is a NEW pointer. Note that I is a pointer. Note how the change to I (I=42) in FOOBAR is returned to main. int main(void) { int *I; I = (int*)calloc(1, sizeof(int)); *I = 99; printf("MAIN: %d %pn", *I, I); FOOBAR(&I); printf("MAIN: %d %pn", *I, I); return 0; } Note how the address of I in FOOBAR and main are now different! The address of I in FOOBAR and I in main is the same. This tells us that they are in fact the same variable (refer to the same memory location). MAIN: 99 0 xae 2030 MAIN: 42 0 xae 2050 Note that the original address that I pointer to is now lost (dangling pointer) – not good!

REVIEW PASSING ------// Simple variable. int main(void) { int i; i = 55; FOO(i); // By value BAR(&i); // By reference } // Simple pointer variable. int main(void) { int *j; j = (int*)calloc(1, sizeof(int)); *j = 100; FOO(*j); // By value BAR(&(*j)); // By reference BAR(j); // By reference } PASSING ------// Pointer by reference. int main(void) { int *k; k = (int*)calloc(1, sizeof(int)); *k = 999; FOOBAR(&k); // Address by reference } RECEIVING ----// By value. void FOO(int I) { I = 42; printf("FOO: %dn", I); } // By reference. void BAR(int *I) { *I = 42; printf("BAR: %dn", *I); } Note the receiving end is usually the same regardless if a pointer or simple variable is being passed to the function. RECEIVING ----// Pointer by reference. void FOOBAR(int *(*I)) { *I = (int*)calloc(1, sizeof(int)); *(*I) = 42; printf("FOOBAR: %dn", *(*I)); }

- Slides: 8