Understanding the C++ const Keyword with Examples

Understanding the C++ const Keyword with Examples


The const keyword is one of the most useful tools you will learn as a beginner in C++. It marks values as read-only through a given expression so you (or other parts of the program) cannot accidentally modify them. In this quick guide to “C++ const keyword with examples,” you will learn what const means, how to use it in variables, parameters, references, pointers, and member functions, along with common mistakes to avoid. If you are a student or new to C++, mastering const will immediately make your code safer and clearer.

Quick takeaways for C++ const keyword with examples

  • const makes a value read-only through that expression; it is not automatically a compile-time constant.
  • Prefer const T& for large function parameters to avoid copies and prevent mutation.
  • Mark member functions that don’t change observable state as const to preserve const-correctness.
  • Use constexpr for true compile-time constants; constinit (C++20) for guaranteed static initialization.
  • For pointers/references, remember: “const applies to what’s on its left (or right if nothing is on the left).”

What does const mean in C++?

C++ const keyword with examples: const variable, const pointer, and pointer-to-const shown with locks and memory arrows
C++ const keyword with examples: const variable vs const pointer vs pointer to const

In C++, const is a type qualifier. It tells the compiler that something cannot be changed through that expression. For example, a const int variable cannot be assigned a new value after it is initialized.

Important: const by itself does not mean “compile-time constant.” A const variable can still hold a value that is only known at runtime. For true compile-time constants you usually use constexpr (explained later).

Example: Simple const variable

Code
#class="cd-package">include <iostream>
int main() {
    const int maxScore = 100;    // read-only after this point
    std::cout << "Max score: " << maxScore << "n";

    // maxScore = 200; // Uncommenting this line would cause a compile error
    return 0;
}
Output
Max score: 100

Why beginners should use const

Pass-by-const-reference vs copy in C++: locked container flows without duplication for speed and safety
C++ const keyword with examples: pass large containers by const reference to avoid copies
  • Prevents accidental changes to values that should not change (safer code).
  • Documents your intent clearly for readers and tools.
  • Enables const-correct APIs (easier to reason about and maintain).
  • Can help the compiler optimize in some cases.

How to use const in C++ (basic syntax)

Most commonly, you will see const used with variables and function parameters.

C++ const variables

Code
#class="cd-package">include <iostream>
#class="cd-package">include <string>

int readUserAge() {
    int age;
    std::cin >> age;
    return age;
}

int main() {
    std::cout << "Enter age: ";
    const int userAge = readUserAge(); // const, but not necessarily compile-time constant
    std::cout << "Your age is: " << userAge << "n";

    // userAge = 21; // would be an error if uncommented
    return 0;
}
Output
Enter age: 20
Your age is: 20

Const parameters: by value vs by reference

When passing by value, marking a parameter as const only affects the function’s local copy; it doesn’t change how the caller can use their original value. For larger objects, prefer passing by const reference (const T&) to avoid copying while still protecting against modification.

Code
#class="cd-package">include <iostream>
#class="cd-package">include <string>

void printLenByValue(const std::string s) { // const applies only inside the function
    std::cout << "Length (by value): " << s.size() << "n";
}

void printLenByConstRef(const std::string& s) { // no copy, cannot modify s
    std::cout << "Length (by const ref): " << s.size() << "n";
}

int main() {
    std::string name = "CodDesire";
    printLenByValue(name);       // copies ___CDPHSTR5___
    printLenByConstRef(name);    // no copy

    // Works with temporaries too (lifetime handled by the call):
    printLenByConstRef(std::string("C++ Learner"));
    return 0;
}
Output
Length (by value): 9
Length (by const ref): 9
Length (by const ref): 11

Const with pointers and references

This is where many beginners get confused. A helpful rule to read declarations is: “const applies to what’s on its left (or right if there’s nothing on the left).”

  • const int* p — pointer to const int (you can’t modify the int via p).
  • int* const p — const pointer to int (pointer cannot change, but the int can).
  • const int* const p — const pointer to const int.

Pointers and references: const cheat sheet (quick reference)

Declaration Meaning Modify pointee? Reseat pointer? Examples
const int* p or int const* p Pointer to const int No Yes *p = 5; // error
p = &other; // ok
int* const p Const pointer to int Yes No *p = 5; // ok
p = &other; // error
const int* const p Const pointer to const int No No *p = 5; // error
p = &other; // error
const int& r Reference to const int No N/A (references don’t reseat) r = 5; // error
binds to temporaries // ok

Example: Pointers to const and const pointers

Code
#class="cd-package">include <iostream>

int main() {
    int value = 10;

    const int* p1 = &value; // pointer to const int (can't modify *p1)
    // *p1 = 20; // error if uncommented
    p1 = &value; // can reseat p1

    int* const p2 = &value; // const pointer to int (can't reseat p2)
    *p2 = 20;               // but can modify the pointee
    // p2 = &value; // error if uncommented

    const int* const p3 = &value; // const pointer to const int
    // *p3 = 30; // error if uncommented
    // p3 = &value; // error if uncommented

    std::cout << "value: " << value << "n";
    return 0;
}
Output
value: 20

Const reference in C++ explained

A const reference (const T&) can bind to both lvalues and temporaries (rvalues). When a temporary is bound directly to a const reference, its lifetime is extended to match the reference’s lifetime. This is both efficient and safe for function parameters and local bindings.

Example: Lifetime extension with const reference

Code
#class="cd-package">include <iostream>
#class="cd-package">include <string>

std::string make_full_name() {
    return "Ada Lovelace";
}

int main() {
    const std::string& ref = make_full_name(); // temporary bound to const ref; lifetime extended
    std::cout << ref << "n"; // safe to use
    return 0;
}
Output
Ada Lovelace

C++ const functions and methods (const member function example)

In classes, mark methods that do not change the object’s observable state as const. This lets you call them on const objects and documents that they won’t modify members (unless they are marked mutable).

Example: const member function

Code
#class="cd-package">include <iostream>

class Counter {
    int value_ = 0;
class="cd-keyword cd-access">public:
    void increment() { ++value_; }
    int value() const { return value_; } // does not modify the object
};

int main() {
    Counter c;
    c.increment();
    c.increment();
    std::cout << "Value: " << c.value() << "n";

    const Counter cc = c;
    std::cout << "Const view: " << cc.value() << "n";
    // cc.increment(); // would be an error: cannot call non-const on const object
    return 0;
}
Output
Value: 2
Const view: 2

When should I use const in C++ code?

  • Constants and configuration that should not change after initialization: const int Max = 10;.
  • Function parameters for large objects: prefer const T& to avoid copies and disallow mutation.
  • Getters and query-like member functions: mark them const.
  • Local variables you do not intend to modify: using const reduces mistakes and clarifies intent.
  • Pointers and references: use const to prevent mutation through that access path.

Note: Adding const to a parameter passed by value doesn’t affect the caller and is mostly a local choice. Prefer const references for expensive-to-copy types instead.

Difference between const and constexpr (and constinit, #define)

Beginners often ask for a “difference between const and constexpr in C++ simple explanation.” Here’s a quick comparison along with #define and constinit:

Feature What it means When to use Notes
const Read-only through that expression Protect variables, parameters, references, members from mutation Not necessarily a compile-time constant
constexpr Must be initialized with a constant expression; usable at compile time True compile-time constants (sizes, array bounds, switch cases) Functions can also be constexpr; evaluated at compile time when possible
constinit (C++20) Ensures static/thread storage variables are initialized at compile time Globals with guaranteed initialization order and speed Variable remains mutable unless also const
#define Preprocessor macro (text replacement) Legacy constants or conditional compilation No type safety or scope; prefer constexpr/const

How to choose: const, const&, constexpr, constinit

Start: What are you declaring?
A named constant value?

If it must be known at compile time → use constexpr.
If not strictly compile-time → use const.

A function parameter?

Small/trivial type → pass by value.
Large/expensive to copy → pass const T&.

A member function?

Does not modify observable state → mark const.
Otherwise → non-const.

A static/global with required compile-time initialization?

Use constinit (C++20). Add const if it must be read-only.

Examples: const vs constexpr vs constinit

Code
#class="cd-package">include <iostream>
#class="cd-package">include <ctime>

// Prefer constexpr for real compile-time constants:
constexpr int DaysInWeek = 7;

// const can be runtime-initialized:
int runtime_value() { return std::time(nullptr) % 10; }
const int ModValue = runtime_value(); // not a compile-time constant

// constinit (C++20) ensures compile-time initialization for statics:
constinit int GlobalCount = 0; // still mutable unless also const

int main() {
    std::cout << "DaysInWeek: " << DaysInWeek << "n";
    std::cout << "ModValue: " << ModValue << "n";
    GlobalCount += 1; // allowed
    std::cout << "GlobalCount: " << GlobalCount << "n";
    return 0;
}
Output
DaysInWeek: 7
ModValue: 3
GlobalCount: 1

Common mistakes and how to avoid them

  • Thinking “const means compile-time constant.” Use constexpr for compile-time constants; const alone can be runtime-initialized.
  • Using const on by-value parameters to “protect the caller.” Top-level const on a copy affects only the function body, not the caller.
  • Forgetting to mark read-only member functions as const. This blocks use on const objects and weakens const-correctness.
  • Assuming const implies thread safety. A const function may still read shared state or modify mutable members; thread safety is a separate concern.
  • Abusing const_cast. Casting away const and then modifying an object originally declared const results in undefined behavior.
  • Making many data members const to “freeze” the object. This can prevent move/assignment and complicate types. Prefer const-correct interfaces instead.

C++ const keyword explained for beginners: a quick practice

Here’s a small program that brings together const variables, const references, and const member functions.

Code
#class="cd-package">include <iostream>
#class="cd-package">include <string>

class Student {
    std::string name_;
    int score_ = 0;
class="cd-keyword cd-access">public:
    Student(std::string name, int score) : name_(std::move(name)), score_(score) {}
    void addBonus(int bonus) { score_ += bonus; }  // mutates

    // const member function: safe to call on const objects
    std::string name() const { return name_; }     
    int score() const { return score_; }          
};

void printStudent(const Student& s) { // const reference: no copy, no mutation
    std::cout << s.name() << " has score " << s.score() << "n";
}

int main() {
    const int Bonus = 5; // read-only constant value

    Student s("Riya", 90);
    s.addBonus(Bonus);

    const Student cs = s; // const view of the same student
    printStudent(cs);     // calls only const member functions

    // cs.addBonus(10); // would be an error if uncommented
    return 0;
}
Output
Riya has score 95

People also ask: quick FAQ

What does the const keyword do in C++?

const marks an object as read-only through that expression. You cannot modify a const object or call non-const member functions on it. This helps you write safer, clearer code.

When should I use const in C++ code?

Use const for values that shouldn’t change, for function parameters passed by const reference, and for class methods that don’t modify the object’s state. This is the essence of const-correctness.

How do I write a const variable or parameter in C++?

Variables: const int x = 10;. Parameters: void f(const std::string& s). For pointers: const int* p (pointer to const int) and int* const p (const pointer to int).

What is a const member function in C++ and why use it?

A const member function guarantees it won’t modify the object’s observable state. It lets you call the function on const objects and communicates intent clearly.

What is the difference between const, constexpr, and #define in C++?

const prevents modification at runtime; constexpr creates compile-time constants (when used with constant expressions); #define is a preprocessor macro without type safety or scope. Prefer constexpr or const over #define for constants.

More examples: const parameter and reference

Below is a compact “how to declare const variables in C++ with example” and “C++ const parameter and reference example.”

Code
#class="cd-package">include <iostream>
#class="cd-package">include <vector>

int sum(const std::vector<int>& v) { // const reference: no copy, read-only
    int total = 0;
    for (int x : v) total += x;
    return total;
}

int main() {
    const int limit = 4; // const variable
    std::vector<int> data = {1, 2, 3, 4};
    std::cout << "Limit: " << limit << ", Sum: " << sum(data) << "n";
    return 0;
}
Output
Limit: 4, Sum: 10

Tips for reading const with pointers

  1. Read right-to-left at the identifier: int* const p — “p is a const pointer to int.”
  2. const int* p — “p is a pointer to const int.”
  3. Use parentheses when in doubt to clarify intent.

Where to learn next

Keep practicing “C++ const keyword with examples” alongside related topics like references, pointers, and classes. Explore more C++ tutorials on CodDesire here: C++ Tutorials at CodDesire.

Sources / Further reading

Subscribe
Notify of
guest
0 Comments
Oldest
Newest Most Voted