Const-ness in C++

Rishabh Agarwal
3 min readMay 21, 2023

--

Photo by Jeppe Hove Jensen on Unsplash

Other stories that you may like —

  1. Copying in C++
  2. Access Specifiers in C++
  3. Constant Variables in C++
  4. Classes in C++
  5. Static Members in C++

I have already discussed about Constant Variables in C++ in one of our earlier story. I highly encourage you checking that!

In this story, I wanted to talk about Const-ness with respect to classes in C++. By the end of this story you will be able to answer questions like —

  • What is the difference between a constant and a non-constant object of a class?
  • What is the purpose of const member functions in C++?
  • What is the semantics behind const data members in a C++ class?

With all these questions in mind, let us begin with today’s story!

Understanding “this” pointer

All the member functions in C++ have access to a secret hidden pointer called ‘this’. This ‘this’ pointer points to the memory location of the current object.

For a class MyClass, following will be the definition of this pointer.

MyClass* const this; 

Note that ‘this’ pointer is a constant pointer i.e., it can not be changed to point to some other object. This however does not mean that the pointed data is constant. (You may want to check this if this is not making sense!)

Here is an example on how to use the this pointer.

class MyClass {
int myDataMember;
public:
MyClass(int myDataMember) : myDataMember(myDataMember) {}
void setMyDataMember(int value) {
// this pointer is available implicitly inside member functions
this -> myDataMember = value;
}
void print() {
std::cout << myDataMember << std::endl;
}
};

Constant Objects

Like variables of built-in type, objects of user-defined types can also be made constant. If an object is marked constant, none of its data members can be changed.

Marking an object constant is same as marking variables constant.

const MyClass myClass(5);

A constant object can not be used to invoke normal methods of the class, since those methods can modify the data members. So, something like the following will result in compilation error.

myClass.setDataMember(10); // Error!
myClass.print(); // Error!

Reader might reason out that setDataMember erroring out makes sense since it tries to change the data member, but why would print method error out? It does not even modify any data members. To understand this we would need to dig a little deeper.

The signature of this pointer is slightly different when the object is marked as constant.

const MyClass* const this; // Constant Pointer to Constant Object

However, normal member functions expects the signature of the this pointer to be as follows.

MyClass* const this; // Constant Pointer to Non-Constant Object

Compiler can not convert a pointer to constant data to a pointer to non-constant data. This is why all calls to normal function calls break when the object is marked constant.

Okay… So how to solve this issue? Hint: Const Member Functions!

Constant Member Functions

Member functions with the keyword const placed between the method’s header and body are called as constant member functions. Inside these methods, no data members can be changed or modified.

void print() const { std::cout << myDataMember << std::endl; }

A constant member function expects the this pointer to be pointing to constant data. Thus, constant objects can safely call const member functions.

Also, since compiler can easily convert a pointer to non-constant data to a pointer to constant data, all non-constant objects can also access the const member functions.

All member functions that do not need to change the data members must be marked as const!

Constant Data Members

Often we want that some data members of an object should not be changed once they are initialised. To achieve this, C++ provides us with the functionality of marking data members as constant.

Const data members can not be changed even from a non-constant member functions. These should be initialised only through constructor’s initialiser lists.

With this we come to the end of this article. I hope you learned something new and exciting today. 🙂

To check more such articles on C++, check my “in C++” series.

Also, if you like my work, show some appreciation by hitting that like button!

--

--

Rishabh Agarwal

Software Developer 2 @ Schrödinger | IIT CSE Graduate - Writes about Software Engineering!