Pointers are at the heart of C. When you crack this subject, you have got the worst of C behind you. Before you tackle pointers though, you should get a grip on arrays.
To understand pointers, it may be worth understanding how normal variables are stored. If you disagree, Click here to move on.
What does the following program realy mean?
main() { int Length; } |
In my mind, it means, reserve enough storage to hold an integer and assign the variable name 'Length' to it. The data held in this storage is undefined. Graphically it looks like:
(Address) (Data) ---- ---- | F1 | <------- Length |----|----| | F2 | | |----|----| | F3 | | |----|----| | F4 | | ---------To put a known value into 'Length' we code,
main() { int Length; Length = 20; } |
(Address) (Data) ---- ---- | F1 | 00 <------- Length |----|----| | F2 | 00 | |----|----| | F3 | 00 | |----|----| | F4 | 14 | ---------Finally, if the program is expanded to become
main() { int Length; Length = 20; printf("Length is %d\n", Length); printf("Address of Length is %p\n", &Length); } |
Length is 20 Address of Length is 0xF1Please note the '&Length' on the second printf statement. The & means address of Length. If you are happy with this, you should push onto the pointers below.
main() { int *Width; } |
(Address) (Data) ---- ---- | F1 | <------- Width |----|----| | F2 | | |----|----| | F3 | | |----|----| | F4 | | ---------So far, this variable looks the same as above, the value stored at 'Width' is unknown. To place a value in 'Width' you could code.
main() { int *Width; /* 1 */ Width = (int *)malloc(sizeof(int)); /* 2 */ *Width = 34; /* 3 */ } |
(Address) (Data) ---- ---- | F1 | 00 <------- Width |----|----| (Data) (Adress) | F2 | 00 | --------- |----|----| -------> 00 | D1 | | F3 | 00 | | |----|----| |----|----| *Width| | 00 | D2 | | F4 | D1 | ------- |----|----| --------- | 00 | D3 | |----|----| | 22 | D4 | ---------Statements 2 and 3 are important here: 2) The malloc function reserves some storage and puts the address of the storage into Width. 3) *Width puts a value into the storage pointed to by Width. Unlike the Length = 20 example above, the storage pointed to by 'Width' does NOT contain 34 (22 in Hex), it contains the address where the value 34 can be found. The final program is...
main() { int *Width; Width = (int *)malloc(sizeof(int)); *Width = 34; printf(" Data stored at *Width is %d\n", *Width); printf(" Address of Width is %p\n", &Width); printf("Address stored at Width is %p\n", Width); } |
Data stored at *Width is 34 Address of Width is 0xF1 Address stored at Width is 0xD1 |
main() { int count; /* an integer variable */ int *pcount; /* a pointer to an integer variable */ float miles; /* a floating point variable. */ float *m; /* a pointer */ char ans; /* character variable */ char *charpointer; /* pointer to a character variable */ } |
main() { char colours[3][6]={"red","green","blue"}; }The code above has defined an array of 3 elements, each pointing to 6 character strings. You can also code it like this. Which is actually more descriptive because it indicates what is actually going on in storage.
main() { char *colours[]={"red","green","blue"}; }Graphically it looks like this:
colours *colours *(colours+2) **colours | | | | | | | | V V V | --- ----------- | | |---->| | | | | --- ----------- | | | | V | | | ----------------------- --------------->| r | e | d | | | | | | ----------------------- | | | | ----------------------- ---|-------->| g | r | e | e | n | | | ----------------------- | | ----------------------- -------->| b | l | u | e | | | ----------------------- A A | | | | **(colours+2) *(*(colours+2)+3) |
printf("%s \n", colours[1]); printf("%s \n", *(colours+1))will both return green.
main() { char colour[]="red"; printf("%s \n",colour); } |
main() { char *colour="red"; printf("%s \n",colour); } |
int func(void *Ptr); main() { char *Str = "abc"; func(Str); } int func(void *Ptr) { printf("%s\n", Ptr); } |
main() { char **DoublePtr; } |
#include |
// declare array of function pointer of type void func(void) void(*function_array[])(void) = { case1function, // &case1function, case2function, // &case2function, ... }; void not_a_switch(int input) { // execute whichever function is at array index "input" function_array[input](); // (*function_array[input])(); } |