GV

GeezerVison

The World Wide Web, restored to 800 pixels of glory.

Home|About|Gaming cabinet|Archives|How it works|Starter sites

On this site

  • Python Technologies
  • Databases
  • Computer Programming
  • Web Development
  • Java Technologies
  • Computer Science
  • Mobile Development
  • Big Data & Analytics
  • Microsoft Technologies
  • DevOps
  • Latest Technologies
  • Machine Learning
  • Digital Marketing
  • Software Quality

This view

  • Original page
  • New address

GeezerVison is showing www.tutorialspoint.com — nullptr in C++

C++ Tutorial
  • C++ Home
  • C++ Overview
  • C++ Environment Setup
  • C++ Basic Syntax
  • C++ Comments
  • C++ Hello World
  • C++ Omitting Namespace
  • C++ Tokens
  • C++ Constants/Literals
  • C++ Keywords
  • C++ Identifiers
  • C++ Data Types
  • C++ Numeric Data Types
  • C++ Character Data Type
  • C++ Boolean Data Type
  • C++ Variable Types
  • C++ Variable Scope
  • C++ Multiple Variables
  • C++ Input Output Operations
  • C++ Basic Input/Output
  • C++ Cin
  • C++ Cout
  • C++ Manipulators
  • Type System & Data Representation
  • C++ Modifier Types
  • C++ Storage Classes
  • C++ Constexpr Specifier
  • C++ Numbers
  • C++ Enumeration
  • C++ Enum Class
  • C++ References
  • C++ Date & Time
  • C++ Operators
  • C++ Operators
  • C++ Arithmetic Operators
  • C++ Relational Operators
  • C++ Logical Operators
  • C++ Bitwise Operators
  • C++ Assignment Operators
  • C++ sizeof Operator
  • C++ Conditional Operator
  • C++ Comma Operator
  • C++ Member Operators
  • C++ Casting Operators
  • C++ Pointer Operators
  • C++ Operators Precedence
  • C++ Unary Operators
  • C++ Scope Resolution Operator
  • C++ Control Statements
  • C++ Decision Making
  • C++ if Statement
  • C++ if else Statement
  • C++ Nested if Statements
  • C++ switch Statement
  • C++ Nested switch Statements
  • C++ Loop Types
  • C++ while Loop
  • C++ for Loop
  • C++ do while Loop
  • C++ Foreach Loop
  • C++ Nested Loops
  • C++ Jump Statements
  • C++ break Statement
  • C++ continue Statement
  • C++ goto Statement
  • C++ Return Values
  • C++ Strings
  • C++ Strings
  • C++ Loop Through a String
  • C++ String Length
  • C++ String Concatenation
  • C++ String Comparison
  • C++ Functions
  • C++ Functions
  • C++ Multiple Function Parameters
  • C++ Recursive Function
  • C++ Function Overloading
  • C++ Function Overriding
  • C++ Default Arguments
  • C++ Arrays
  • C++ Arrays
  • C++ Multidimensional Arrays
  • C++ Pointer to an Array
  • C++ Passing Arrays to Functions
  • C++ Return Array from Functions
  • C++ Array Decay
  • C++ Structure & Union
  • C++ Structures
  • C++ Unions
  • C++ Pointers
  • C++ Pointers
  • C++ Dereferencing
  • C++ Modify Pointers
  • C++ Smart Pointers
  • C++ Class and Objects
  • C++ Object Oriented
  • C++ Classes & Objects
  • C++ Class Member Functions
  • C++ Class Access Modifiers
  • C++ Static Class Members
  • C++ Static Data Members
  • C++ Static Member Function
  • C++ Inline Functions
  • C++ this Pointer
  • C++ Friend Functions
  • C++ Pointer to Classes
  • C++ Constructors
  • C++ Constructor & Destructor
  • C++ Default Constructors
  • C++ Parameterized Constructors
  • C++ Copy Constructor
  • C++ Constructor Overloading
  • C++ Constructor with Default Arguments
  • C++ Delegating Constructors
  • C++ Constructor Initialization List
  • C++ Dynamic Initialization Using Constructors
  • C++ Destructors
  • C++ Virtual Destructor
  • C++ Inheritance
  • C++ Inheritance
  • C++ Multiple Inheritance
  • C++ Multilevel Inheritance
  • C++ Object-oriented
  • C++ Overloading
  • C++ Polymorphism
  • C++ Abstraction
  • C++ Encapsulation
  • C++ Interfaces
  • C++ Virtual Function
  • C++ Pure Virtual Functions & Abstract Classes
  • C++ Override Specifiers
  • C++ Final Specifiers
  • C++ Design Patterns
  • C++ Creational Design Patterns
  • C++ Singleton Design Pattern
  • C++ Factory Method Design Pattern
  • C++ Abstract Factory Pattern
  • C++ Prototype Design Pattern
  • C++ Structural Design Patterns
  • C++ Facade Design Pattern
  • C++ Iterator Design Pattern
  • C++ Mediator Design Pattern
  • C++ Memento Design Pattern
  • C++ Observer Design Pattern
  • C++ State Design Pattern
  • C++ Strategy Design Pattern
  • C++ Template Method Design Pattern
  • C++ Visitor Design Pattern
  • C++ Behavioural Design Pattern
  • C++ File Handling
  • C++ Files and Streams
  • C++ Reading From File
  • C++ Advanced
  • C++ Exception Handling
  • C++ Dynamic Memory
  • C++ Move Semantics
  • C++ Namespaces
  • C++ Templates
  • C++ Preprocessor
  • C++ Signal Handling
  • C++ Multithreading
  • C++ Web Programming
  • C++ Socket Programming
  • C++ Concurrency
  • C++ Advanced Concepts
  • C++ Lambda Expression
  • C++ nullptr
  • C++ unordered_multiset
  • C++ Chain of Responsibility
  • C++ Structural Design Patterns
  • C++ Adapter Pattern
  • C++ Bridge Pattern
  • C++ Composite Pattern
  • C++ Decorator Pattern
  • C++ Command Pattern
  • C++ Proxy Pattern
  • C++ Useful Resources
  • C++ Questions and Answers
  • C++ Quick Guide
  • C++ Cheatsheet
  • C++ STL Tutorial
  • C++ Standard Library
  • C++ Useful Resources
  • C++ Discussion
  • C++ Online Compiler
Selected Reading
  • UPSC IAS Exams Notes
  • Developer's Best Practices
  • Questions and Answers
  • Online Resume Builder
  • HR Interview Questions
  • Computer Glossary
  • Who is Who

nullptr in C++



Previous
Quiz
Next

The nullptr keyword in C++ represents a null pointer value which was earlier represented using NULL or 0. It was introduced in C++11 and is of type std::nullptr_t. The nullptr is a type-safe pointer that is implicitly convertible and can be compared to any pointer.

The syntax for defining a nullptr is given below −

int* ptr = nullptr; // ptr is a null pointer of type int*

Example

The following example demonstrates how to use nullptr in C++

#include <iostream>
using namespace std;

int main() {
	int *ptr = nullptr; // ptr is a null pointer

	if (ptr == nullptr)
	{
		cout << "Pointer is null." << endl;
	}
	else
	{
		cout << "Pointer is not null." << endl;
	}

	int x = 10;
	ptr = &x;

	if (ptr != nullptr)
	{
		cout << "Pointer now points to: " << *ptr 
             << endl;
	}

	return 0;
}

The output of the above code is given below −

Pointer is null.
Pointer now points to: 10

Why Do We Need nullptr?

We need nullptr because of the following problems caused by using NULL or 0

  • Ambiguity in Function Calling
  • Problem in Function Overloading
  • Type-Safety Problem

Ambiguity in Function Calling

Calling a function with value '0' to represent NULL creates an ambiguity because compiler treats '0' as an integer value rather than a null pointer.

In this example, we are calling display() function by passing value as '0'. It calls the function that has an int parameter rather than calling the function that has a pointer in its parameter.

#include <iostream>
using namespace std;

void display(int n){
   cout << "Calling display function with int" << endl;
}

void display(int *p){
   cout << "Calling display function with int*" << endl;
}

int main(){
   display(0); // Ambiguous call as Compiler treats 0 as integer
   return 0;
}

The output of the above code is given below −

Calling display function with int

Solution: Below is the solution to above problem where we have used nullptr that calls the display() function that has a pointer in its parameter −

#include <iostream>
using namespace std;

void display(int n){
   cout << "Calling display function with int" << endl;
}

void display(int *p){
   cout << "Calling display function with int*" << endl;
}

int main(){
   display(nullptr); 
   return 0;
}

The output of the above code is given below −

Calling display function with int*

Problem in Function Overloading

If you call an overloaded function with NULL value, it will cause a compilation error. The NULL is valid for both parameters that is int and int*. So, in this confusion compiler throws an error. Below is an example to demonstrate this problem.

#include <iostream>
using namespace std;

class Demo{
public:
	void show(int n)
	{
		cout << "Calling show() function with int" << endl;
	}

	void show(int *p)
	{
		cout << "Calling show() function with int*" << endl;
	}
};

int main() {
	Demo obj;
	// Ambiguous call with NULL
	obj.show(NULL);
	return 0;
}

The output of the above code is given below −

main.cpp: In function 'int main()':
main.cpp:22:17: error: call of overloaded 'show(NULL)' is ambiguous
   22 |         obj.show(NULL);
      |         ~~~~~~~~^~~~~~
main.cpp:7:14: note: candidate: 'void Demo::show(int)'
    7 |         void show(int n)
      |              ^~~~
main.cpp:12:14: note: candidate: 'void Demo::show(int*)'
   12 |         void show(int *p)
      |              ^~~~

Solution: Below is the solution to above problem where we have used nullptr that calls the display() function that has a pointer in its parameter −

#include <iostream>
using namespace std;

class Demo {
public:
	void show(int n)
	{
		cout << "Calling show() function with int" << endl;
	}

	void show(int *p)
	{
		cout << "Calling show() function with int*" << endl;
	}
};

int main() {
	Demo obj;
	obj.show(nullptr); // Correctly calls int* function
	return 0;
}

The output of the above code is given below −

Calling show() function with int*

Type-Safety Problem

The NULL is treated as an integer since it is defined with '0'. It creates the same ambiguity as the above two problems. It is solved using nullptr because nullptr is type-safe unlike NULL and it is implicitly convertible to any pointer type.

#include <iostream>
using namespace std;

int main() {
	int* ptr = nullptr;

	cout << "Comparing with NULL" << endl;
	if (ptr == NULL) {
		cout << "NULL is TRUE" << endl;
	} else {
		cout << "NULL is FALSE" << endl;
	}

	cout << "\nComparing with nullptr" << endl;
	if (ptr == nullptr) {
		cout << "nullptr is TRUE" << endl;
	} else {
		cout << "nullptr is FALSE" << endl;
	}

	int value = 0;

	// NULL will be treated as integer 0
	if (value == NULL) {
		cout << "value(0) = NULL is TRUE" << endl;
	}
	return 0;
}

The output of the above code is given below −

main.cpp: In function 'int main()':
main.cpp:24:22: warning: NULL used in arithmetic [-Wpointer-arith]
   24 |         if (value == NULL) 
      |                      ^~~~
Comparing with NULL
NULL is TRUE

Comparing with nullptr
nullptr is TRUE
value(0) = NULL is TRUE

NULL vs nullptr

The difference between NULL and nullptr is mentioned in the table below −

NULL nullptr
It is an integer constant that represents either 0 or 0L. In C, it is represented as ((void*)0). It is a pointer literal of type std::nullptr_t.
It is not type-safe as it may be treated as an int. It is type-safe as it represents only pointer.
It can be assigned to int values. It can not be assigned to an int value, as it will show an error.
In function overloading, there is ambiguity when calling the function. It prevents the problem of ambiguity in function overloading.
Example: int* p = NULL; Example: int* p = nullptr;

Nullptr Use Cases

The main purpose of the nullptr is to assign a null value to any pointer. Here are some use cases where a nullptr can be used.

Resetting Pointers After Deletion

A pointer needs to be assigned to a null value after deletion to avoid a dangling pointer. Here is an example to reset pointer to null after cleaning up the memory.

#include <iostream>
using namespace std;

int main() {
	int *ptr = new int(57);
	cout << "Value: " << *ptr << endl;

	delete ptr;    // Free memory
	ptr = nullptr; // Resetting pointer

	if (ptr == nullptr)
		cout << "Pointer reset successful." << endl;

	return 0;
}

The output of the above code is given below −

Value: 57
Pointer reset successful.

Checking Pointer Validity

You should first check that the pointer is not null before accessing it to avoid crashes. Here is an example to check if the pointer ptr is a null pointer or not.

#include <iostream>
using namespace std;

int main() {
	int *ptr = nullptr;
	if (ptr != nullptr)
		cout << "Pointer value: " << *ptr << endl;
	else
		cout << "It is a null pointer." << endl;

	return 0;
}

The output of the above code is given below −

It is a null pointer.	

Safe Object Initialization for Null Value

The nullptr can be used for setting a pointer to null without causing any error or any garbage value. Here is an example to assign a null value to represent an empty linked list −

#include <iostream>
using namespace std;

struct Node {
	int data;
	Node *next;
};

int main() {
	Node *head = nullptr; // Empty linked list

	if (head == nullptr)
		cout << "Linked list is empty." << endl;

	return 0;
}

The output of the above code is given below −

Linked list is empty.

Function Overloading Resolution

The nullptr is also used to resolve the ambiguity in function overloading. Here is an example.

#include <iostream>
using namespace std;

void show(int n){
   cout << "Integer called." << endl;
}

void show(int *p){
   cout << "Pointer called." << endl;
}

int main(){
   show(nullptr); // Calls pointer
   return 0;
}

The output of the above code is given below −

Pointer called.

Conclusion

In this chapter, we have understood that the nullptr in C++ is used when we need a null pointer. Before C++11, NULL was used, but it had various problems which is addressed by the nullptr. We have also discussed various use cases of nullptr with examples.

Tutorix - AI Tutor
Previous Quiz Next
Advertisements
You are visitor 01402503 — GeezerVison does not store the pages you look up.
Best viewed with Netscape Navigator 4.7 or Internet Explorer 6 at 800×600. No cookies required.