The pointer-to-a-pointer variable does have a purpose, but fortunately it’s a very specific and rare purpose. And, no, that purpose isn’t to make you wish you had learned to program in Java.
For review, here is the code concocted for last week’s Lesson, the full code, which includes the final line:
#include <stdio.h> int main() { int i; int *ptr; int **ptr2ptr; i = 4; ptr = &i; /* initialize ptr2ptr: */ ptr2ptr = &ptr; printf("i is %d\n",i); printf("&i is %p\n",&i); printf("*ptr is %d\n",*ptr); printf("ptr is %p\n",ptr); /* new stuff here: */ putchar('\n'); printf("&ptr is %p\n",&ptr); printf("ptr2ptr is %p\n",ptr2ptr); printf("*ptr2ptr is %p\n",*ptr2ptr); printf("**ptr2ptr is %d\n",**ptr2ptr); return(0); }
Sample output on my PC looks like this:
i is 4
&i is 0028FF18
*ptr is 4
ptr is 0028FF18
&ptr is 0028FF14
ptr2ptr is 0028FF14
*ptr2ptr is 0028FF18
**ptr2ptr is 4
If you think this is a stupid way to get back to the value of variable i
, you’re correct!
No, you didn’t just waste a lot of time.
The pointer-to-a-pointer variable isn’t used to reference a single pointer. And thank goodness! Instead, it’s used to reference an array of pointers. That’s how it’s best put to use. I suppose exceptions to this rule might exist, but I can’t think of any.
When you see a
**ptr
type of variable, it almost always refers to an array of pointers.
Here’s a quick review based on the above code and the stuff I preached in last week’s Lesson:
*ptr
is a pointer variable, one that holds the address of a specific type of variable, such as an int, char, float, and so on.
**ptr
is a pointer-to-a-pointer variable. It can hold the address of another pointer variable. The variable types still have to match, int for int, char for char, and so on.
The way the **ptr
construction is useful is when its value needs to be manipulated. That’s true for all variables, of course. After all, **ptr
is a variable, a word which shares its root in the term vary. It makes no sense to create a **ptr
type of variable unless its value is going to be manipulated.
The **ptr
variable is most useful when it references an array of pointers. The best example I can think of to demonstrate that use is to reference and manipulate an array of strings.
Consider the months array, introduced in an earlier Lesson:
code>char *months[] = { "January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December" };
This array isn’t an array of strings; the strings are created somewhere in memory. The array consists of the starting location for each string — a pointer. Here is Figure 1 from February 8th’s lesson, which shows those memory locations as they appear when dumped in Code::Blocks:

Figure 1. How the months
array looks in memory.
To manipulate items in that array, you use a pointer-to-a-pointer variable. The example below demonstrates how **m
can be used to manipulate the array:
#include <stdio.h> int main() { char *months[] = { "January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December" }; int x; char **m; m = months; for(x=0;x<12;x++) printf("%s\n",*(m+x)); return(0); }
This example is similar to the final example from the Lesson on February 8th. It shows how a pointer array is manipulated by using a **
variable type. Even then, you can get into lots of trouble if you’re not careful.
The pointer-to-a-pointer variable is pretty much on the far fringe of what you do with pointers in C. It’s the harbinger of the Segmentation Fault. Fortunately, beyond code such as what’s shown above, the **
construction isn’t something you deal with often in the C language.