Skip to content

Chapter 7 of 31

Functions

Design declarations, overloads, value and reference parameters, recursion, and inline functions.

36 minutes 10 quick checksBy Subha Prasad
Lesson 7 of 31Course navigation

Lesson content

Read, practise, then check your understanding

A declaration tells callers a function’s name, parameter types, and return type. A definition supplies its body. Place stable declarations in headers and definitions in source files; include guards or #pragma once prevent repeated header contents.

#include <string_view>

[[nodiscard]] int factorial(int n) {
    if (n < 0) return 0;
    if (n <= 1) return 1;
    return n * factorial(n - 1);
}

void greet(std::string_view name, int times = 1);

Pass small cheap types by value. Use const T& for a large read-only object, T& for a required mutable output, and T* when absence is meaningful. Never return a pointer or reference to a destroyed local object.

Recursion and overloading

Recursion needs a base case and progress toward it. Deep recursion consumes stack space, so an iterative solution may be safer. Overloads share a name but differ in parameter lists; return type alone cannot distinguish them. Default arguments are substituted at the call site and should normally appear in one visible declaration.

inline and constexpr

inline primarily permits identical definitions in multiple translation units; it does not force machine-code inlining. Define short templates and constexpr functions in headers because their definitions must be visible where instantiated or evaluated.

constexpr int square(int value) noexcept {
    return value * value;
}
static_assert(square(6) == 36);

Keep functions focused, name contracts clearly, minimize hidden global effects, and use [[nodiscard]] when ignoring a result is probably a bug.

Knowledge check

Answer every question correctly to complete this chapter.

What declares a function before its definition?
What must recursion contain?
What does inline primarily permit?
How are ordinary parameters passed by default?
Which parameter avoids a copy and disallows mutation?
What is a default argument?
Can a function return a reference to a destroyed local?
What does [[nodiscard]] encourage?
What does a trailing return type look like?
What is function-local static initialization guaranteed to be since C++11?

0 of 10 checks passed

Your progress is saved on this device.