Dynamic Memory Allocation in C++ with Detailed Examples

Updated on August 22, 2024

Article Outline

Dynamic memory allocation in C++ language is a powerful feature that allows programmers to allocate memory at runtime. This is especially useful when the size of the data structure is not known at compile time. The C++ language provides operators ‘new’ and ‘delete’ for dynamic memory management. This article explains everything about the Dynamic Memory Allocation in C++ language.

C++ Program Memory Management

When we execute our program in a computer system. It requires some space to store its instructions,local variables, global variables, and various other functions in C++. It is also known as memory in computers where statements will be stored.

 

There are two types of memory in our computer system: Static Memory and Dynamic Memory.

 

  • Static Memory: This is constant memory allocated by the operating system during a C++ program’s compile time. The operating system internally uses a stack data structure to manage the static memory allocation.

 

  • Dynamic Memory: Dynamic memory can be allocated or de-allocated by the operating system during a C++ program’s runtime. This is more efficient than static memory because we can deallocate and reuse our memory during the program’s runtime.

 

We can divide the memory into four parts which are used by the C++ program:

 

  • Stack Memory
  • Static Data Memory (for Global and Static Variable)
  • Instruction/Statements (Static Memory)
  • Heap (Dynamic Memory)

Memory Management

The Stack Memory

The stack memory stores local variables and function call information. It is based on the LIFO (Last in, First Out) structure, which means that the last piece of data added to the stack is the first one to be removed.

 

  • This memory allocated a constant space during the compile time of a C++ program, this space is known as Stack memory.
  • Stack memory is used to hold functions, different variables and local statements that exist in the function definition.
  • The size of stack memory is limited in the computer system. If too much memory is allocated on the stack, it can lead to a stack overflow, which can cause the program to crash. This is in contrast to heap memory which is larger and can grow dynamically, although it is slower to allocate and deallocate.

The Heap Memory

Heap memory, also known simply as the heap, is a region of a computer’s memory used for dynamic memory allocation. It allows memory blocks of arbitrary sizes to be allocated and deallocated at any time.

 

  • This memory is also known as the dynamic memory in our computer system. It is a large block of memory that is expandable and shrinkable during program execution.
  • The heap memory, which is typically limited in size and can lead to stack overflow errors if overused, can grow as needed(within the limits of the system’s physical and virtual memory). This allows for the creation of large data structures and arrays whose size might not be known at compile time.
  • The heap memory can become fragmented as blocks of memory are allocated and freed in a non-contiguous manner. This fragmentation can lead to inefficient memory usage and potentially slow down allocation and deallocation operations.
*Image
Get curriculum highlights, career paths, industry insights and accelerate your technology journey.
Download brochure

Types of Memory Allocation

We can classify memory into types: static memory allocation and dynamic memory allocation. Understanding these types helps in efficient memory management and ensures the optimal performance of C++ programs.

 

  • Static Memory Allocation: Static memory allocation is performed at compile time; this size and type of memory are determined before the program runs, and the memory is allocated on the stack. This type of allocation is used for variables whose size is known and fixed at compile time.

 

  • Dynamic Memory Allocation: Dynamic memory allocation is performed at runtime using operators like ‘new’ and ‘delete’. The memory is allocated on the heap, and the size can be adjusted as needed during program execution.

Why Dynamic Memory Allocation?

Dynamic memory allocation in C++ is a powerful feature that allows for flexible and efficient memory management at runtime. Let’s examine some reasons why dynamic memory allocation is commonly used in the C++ language.

 

  • Flexibility and Efficiency: The static memory allocation, where the size of data structures must be known at compile-time, dynamic memory allocation allows the allocation of memory for data structures whose sizes can be determined during runtime. This is particularly useful for applications where the amount of data cannot be predicted in advance.

 

  • Efficient Memory Usage: Dynamic memory allocation allows for the creation of data structures that use only as much memory as needed, which can lead to more efficient memory use. This is especially true in cases where data structures need to grow or shrink during the program’s execution.

 

  • Real-Time Systems: Real-time systems need to allocate memory on the fly without causing interruptions. Dynamic memory allocation allows for the management of memory in a way that can meet real-time constraints.

How is it Different from Memory Allocated to Normal Variables?

Operating systems use static memory for allocation for normal data types in C++. For example, int r, double arr[30], char name [30], etc. int r, double arr[10]; char name[20]; etc. This memory is allocated automatically at compile time and de-allocated when the function block or program finishes by the operating system. The operating system uses the dynamic memory allocation for dynamically allocated variables in the program. For example, int *ptr = new int. This memory must be deallocated by the programmer when it is no longer required. Because memory leaks occur when the programmer forgets to deallocate the memory.

Dynamic Memory Allocation & De-allocation Criteria

  • Creating the Dynamic Space in Memory: Create the dynamic memory space in the heap memory. Using the new operator in C++ language.

 

  • Storing its Address in a Pointer: After creating the dynamic space. We have to store the address of the allocated space in a pointer variable. This variable accesses and modifies the contents of the memory block.

 

  • Deleting the Allocated Space: When the developer does not require the memory block. We can delete the allocated space using the delete operator to free up the heap memory in the computer system.

The ‘new’ operator in C++

Dynamic memory allocation is a crucial concept in C++. It allows the creation of objects and arrays whose size is not known at compile time but determined at runtime. In this situation, we can use the ‘new’ operator in the C++ language, which allocates memory at runtime.

 

Syntax of ‘new’ operator

<strong>data_type * ptr = new data_type ;</strong>
  • ptr: This variable stores the address of the type.
  • data_type: It can be any predefined types like int, char, etc or other user-denied data types like classes, and can be used as the data_type with the new operator in C++

 

The following program demonstrates the ‘new’ operator in C++:

 

Program

# include <iostream><strong> </strong> using namespace std ; int main(){ int *ptr = new int ; *ptr = 30 ; cout << " Value at Memory pointed by ptr ="<< *ptr ; }

Output

Value at Memory pointed by ptr =30

Initializing Dynamic Memory

 

Syntax

data_type* ptr_var = new data-type(value);

Example C++ Program

#include <iostream> using namespace std; int main() { // dynamically allocating an integer memory block // with 12 as its initial value int* ptr = new int(50); cout << "Value at memory pointed by ptr= " << *ptr; return 0; }

Output

Value at memory pointed by ptr= 50

The ‘delete’ Operator in C++

In C++ language, the ‘delete’ operator is used to deallocate memory that was previously allocated using the ‘new’ operator. When you allocate memory dynamically, it resides on the heap or free store, and it’s your responsibility to free this memory when it’s no longer needed to prevent memory leaks.

 

Syntax of ‘delete’ operator

delete ptr_variable ;

Syntax to delete an array of memory

delete[] ptr_variable ;

The following program demonstrates the delete program

 

Program

#include <iostream> using namespace std; int main() { int* numbers = new int; *numbers = 505300; cout<<"Visible stars in the sky: "<<*numbers; // stars memory deallocated using the delete operator delete numbers; cout<<"nGarbage value: "<<*numbers; numbers = NULL; return 0; }

Output

Visible stars in the sky: 505300 Garbage value: 0

Dynamic Memory Allocation in C++ for Arrays

The new operator can also allocate a block of memory (an array) of any data type.

 

Syntax

data_type* ptr = new data_type[size_of_the_array] ;

Example

 

char *name = new char[30]

Standard Array Declaration vs Using the ‘new’ operator

In C++ language, We can declare in two primary ways, using standard array declarations and the ‘new operator.  Each method has its own use cases, advantages and limitations. Here’s a detailed comparison of the two approaches:

 

Feature Standard Array Declaration Using ‘new’ Operator
Size The fixed, known at compile time Dynamic, determined at runtime
Memory Allocation Stack  Heap
Deallocation Automatic Manual(using delete[])
Flexibility Limited to compile-time size Flexible, runtime size
Performance Faster Allocation Potentially slower due to heap management

 

The following program with a new operator in C++:

 

Program

#include <iostream> using namespace std; int main() { int* arr = new int[5]; cout << "Enter 5 values in the array: "; for(int i = 0; i < 5; i++){ cin >> arr[i]; } cout << "nArray elements: "; for(int i = 0; i < 5; i++) { cout << arr[i] << " "; } delete [] arr; cout << "nGarbage array values after deallocation of array memory: "; for(int i = 0; i < 5; i++){ cout << arr[i] << " "; } return 0; }

Output

Enter 5 values in the array: 5 20 30 39 3   Array elements: 5 20 30 39 3 Garbage array values after deallocation of array memory: 0 0 13066256 0 3

Dynamic Memory Allocation in C++ for Objects

In the C++ language, we can also allocate dynamic memory for objects. When we create an object of a class, a constructor function is invoked. A constructor is a member function of a class that is used to initialize the object.

 

The following program demonstrates the dynamic memory allocation in C++:

 

Program

#include <iostream> using namespace std; class Cats { public: Cats() { cout << "Cat class constructor invoked!" <<endl; } ~Cats() { cout << "Cat class destructor invoked!" <<endl; } }; int main() { Cats* cat = new Cats; delete cat; return 0; }

Output

Cat class constructor invoked! Cat class destructor invoked!

Comparison with “malloc()”, “calloc()”, and “free()”  functions of C

Let’s understand the malloc() , calloc() and free() library function definition before moving forward:

C Functions Definitions Syntax
malloc() This function is used for dynamic memory allocation. This function returns arguments’ size (in bytes) and returns a void pointer to the allocated pointer’s first byte (cast-data-type*)malloc(size-in-bytes)
calloc() The ‘calloc’ function allocates memory for an array of elements, initializes all bytes in the allocated storage to zero, and then returns a pointer to the memory. void* calloc(size_t num, size_t size);
free() This function is used to clear the allocated space (deallocate) from the heap memory. free(ptr)

“new” vs “malloc()” and “calloc()”

The new operator has similar working as malloc() and calloc() functions. These functions are used to allocate memory during the program execution in C++ and C programs. But when we use a new operator, it invokes the constructor function of the class. But the malloc() and calloc() functions do not invoke the constructor function.

 

Example C++ Program:

#include <iostream> using namespace std; class Animal { public: Animal() { cout << "Animal class constructor invoked!" <<endl; } ~Animal() { cout << "Animal class destructor invoked!" <<endl; } }; int main() { Animal* dog = new(nothrow) Animal; Animal* dogs = new(nothrow) Animal[5]; Animal* cat = (Animal*)malloc(sizeof(Animal)); Animal* cats = (Animal*)calloc(5, sizeof(Animal)); return 0; }

Output

Animal class constructor invoked! Animal class constructor invoked! Animal class constructor invoked! Animal class constructor invoked! Animal class constructor invoked! Animal class constructor invoked!

“delete” vs “free()”

In C++ language, ‘delete’ and free()’ are both used to deallocate dynamically allocated memory.  But they have some significant differences. The ‘delete’ is used to deallocate memory that was allocated with ‘new’, and it also calls the destructor of the object, ensuring proper cleanup of resources.

 

The following program demonstrates the “delete vs free()”:

 

Program

#include <iostream> using namespace std; class Animal { public: Animal() { cout << "Animal class constructor invoked!" <<endl; } ~Animal() { cout << "Animal class destructor invoked!" <<endl; } }; int main() { Animal* dog = new(nothrow) Animal; Animal* cat = (Animal*)malloc(sizeof(Animal)); delete dog; free(cat); return 0; }

Output

Animal class constructor invoked! Animal class destructor invoked!

Conclusion

In this article, we learned about the dynamic memory allocation in C++ language. It is a powerful feature that allows developers to allocate memory at runtime. This provides flexibility in managing memory for various data structures and objects. The ‘new’ and ‘delete’ operators offer a robust mechanism for allocating and deallocating memory, ensuring that constructors and destructors are called, which is essential for resource management and avoiding memory leaks. By understanding these functions, C++ developers can leverage these tools and write more efficient, reliable and maintainable source code.

FAQs
It is the process of allocating memory at runtime using operators like ‘new’ and ‘new[]’. This allows the program to request memory from the heap as needed rather than relying solely on stack memory or static memory allocation.
Dynamically allocated variables live in a piece of memory known as the heap. The running program requests them using the keyword ‘new’.
Stack Memory:  This memory is used for local variables and function calls. This is limited in size and scope. It is fast but not suitable for large or dynamically sized data.   Heap Memory: Managed manually or with smart pointers, used for dynamic memory allocation. It allows for more flexible and larger memory allocation but requires careful management to avoid leaks and fragmentation.

Updated on August 22, 2024

Link
left dot patternright dot pattern

Programs tailored for your success

Popular

Management

Data Science

Finance

Technology

Future Tech

Upskill with expert articles

View all
Hero Vired logo
Hero Vired is a leading LearnTech company dedicated to offering cutting-edge programs in collaboration with top-tier global institutions. As part of the esteemed Hero Group, we are committed to revolutionizing the skill development landscape in India. Our programs, delivered by industry experts, are designed to empower professionals and students with the skills they need to thrive in today’s competitive job market.
Blogs
Reviews
Events
In the News
About Us
Contact us
Learning Hub
18003093939     ·     hello@herovired.com     ·    Whatsapp
Privacy policy and Terms of use

|

Sitemap

© 2024 Hero Vired. All rights reserved