← Back to C Course | Chapter 7: Pointers | Lesson 6 of 9

C Double Pointers

A double pointer is a pointer that points to another pointer, like a note that tells you where to find another note. It is useful for changing a pointer inside a function.
Syntax
c
data_type variable_name = value;
data_type *pointer_name = &variable_name;
data_type **double_pointer = &pointer_name;

**double_pointer;  // the original value

What is a Double Pointer?

You can chain this indirection further -- a triple pointer stores the address of a double pointer -- but in practice, C code rarely goes beyond two levels because the added complexity outweighs the benefit.

Example: What is a Double Pointer?

c
// Include standard input/output (printf, scanf)
#include <stdio.h>
// Program execution starts in main()
int main() {
	// Declare x and set it to 5
	int x = 5;
	int *ptr = &x;
	int **pptr = &ptr;
	// Print formatted text to the screen
	printf("%d", **pptr);
	// Return 0 to signal that the program finished successfully
	return 0;
}

Declaring Double Pointers

int **pptr declares pptr as a pointer to a pointer to an int; the type must match at every level, so you can't assign the address of a plain int pointer to a variable declared with three asterisks.

Example: Declaring Double Pointers

c
// Include standard input/output (printf, scanf)
#include <stdio.h>
// Program execution starts in main()
int main() {
	// Declare x and set it to 5
	int x = 5;
	int *ptr = &x;
	int **pptr = &ptr;
	// Print formatted text to the screen
	printf("%d", **pptr);
	// Return 0 to signal that the program finished successfully
	return 0;
}

Initializing and Referencing

A typical setup looks like: int x = 5; int *ptr = &x; int **pptr = &ptr -- pptr now holds the address where ptr itself is stored, one level of indirection above x.

Example: Initializing and Referencing

c
// Include standard input/output (printf, scanf)
#include <stdio.h>
// Program execution starts in main()
int main() {
	// Declare x and set it to 5
	int x = 5;
	int *ptr = &x;
	int **pptr = &ptr;
	// Print formatted text to the screen
	printf("%d", *ptr);
	// Return 0 to signal that the program finished successfully
	return 0;
}

Double Dereferencing ()

Given the setup above, *pptr yields ptr (the address of x), and **pptr yields the value of x itself (5) -- each asterisk peels back exactly one layer of indirection.

Example: Double Dereferencing ()

c
// Include standard input/output (printf, scanf)
#include <stdio.h>
// Program execution starts in main()
int main() {
	// Declare x and set it to 5
	int x = 5;
	int *ptr = &x;
	int **pptr = &ptr;
	// Print formatted text to the screen
	printf("%d", **pptr);
	// Return 0 to signal that the program finished successfully
	return 0;
}

Practical Uses of Double Pointers

This is essential when a function needs to modify what a pointer points to (not just the value at that address) -- for example, a function that allocates memory and needs the caller's pointer variable itself to be updated to point at the new block.

Example: Practical Uses of Double Pointers

c
// Include standard input/output (printf, scanf)
#include <stdio.h>
void allocate(int **out) {
	static int value = 99;
	*out = &value;
}
// Program execution starts in main()
int main() {
	int *result;
	allocate(&result);
	// Print formatted text to the screen
	printf("%d", *result);
	// Return 0 to signal that the program finished successfully
	return 0;
}
Related Topics
{# common_mistakes/chapter_summary/browser_support: on Hindi pages the view already swaps in the hi_ translation fields (or blanks these out if untranslated), so this renders correctly for both languages without a lang_code check here. #}
Common Mistakes
  1. Dereferencing only once with *pp and expecting the final value, when **pp is needed to reach the original variable.
  2. Using a double pointer that has not been initialized, so dereferencing it crashes.
  3. Confusing *pp (the inner pointer) with **pp (the value it points to).

Login to run this code

C/C++/Java/PHP execution requires a free account. Your code is saved — you'll land right back in the editor after logging in.