Change the Rules of C++ with Defaulted Functions

Change the Rules of C++ with Defaulted Functions

rogrammers have little control over the implicit declarations of the four canonical member functions. The compiler will not generate a default constructor for a class that has a user-declared copy-constructor. This frustrating state of affairs is about to change. The deleted and defaulted functions proposal provides a convenient mechanism for just this type of per-class customization. The following sections will show you how to use defaulted functions.

In certain cases, you need to define a default constructor manually, because the compiler will not implicitly-declare it. Not only is manual constructor definition tedious, it’s also not very efficient.

Use the new =default function specifier to make the compiler generate a member function that wouldn’t be generated otherwise.

Presenting the Problem
Suppose you’re designing a class that requires a user-defined copy constructor:

class C{public: C(const C& rhs);};

Later, when you try to create an object for this class, you get a compilation error:

C obj;//error: no default constructor exists for class CC * pc= new C; //same error

This kind of error can baffle even experienced programmers. Wasn’t the compiler supposed to implicitly declare a default constructor for class C? No, it wasn’t. When you declare a copy constructor in a class, the compiler doesn’t implicitly-declare a default constructor in that class. What if you want the compiler to generate a default constructor for you anyway? In C++03, there’s no way to override these language rules; you simply have to define the missing default constructor manually:

class C{public: C(const C& rhs); C() {} //manual definition of a default constructor};C obj; //OK

Not only is this tedious, the user-defined default constructor is often less efficient than the compiler’s implicitly-defined default constructor.

What a Difference a default Makes
C++09 offers a neat solution to this problem by extending the semantics to the keyword default. To force the compiler to generate a copy constructor for a class that wouldn’t normally get one, declare the default constructor like this:

class C{public: C(const C& rhs); C()=default;};

This way, the compiler will be forced to generate a default constructor for C.

Notice how elegantly this new feature extends the meaning of default, a keyword that already exists in C and C++. To make default‘s new role distinct from its traditional use in switch statements, defaulted functions now adopt pure virtual functions=specifier notation. The =default function specifier can be added to any of the special member functions?not just the constructor.

Author’s Note: By mere coincidence, the word default is used in both default constructors and defaulted functions. Recall that a default constructor is simply a constructor that can be invoked with no arguments. To avoid confusion, I use the phrase “defaulted constructor” to refer to a constructor that is declared with the =default specifier.

Destructors Unleashed
The C++ standard states clearly when the compiler will implicitly declare a destructor for a class and when it won’t. Here too, the rules don’t always meet your design goals. With the =default specifier you can override them.

Suppose you’re designing an interface for an asbtract pointing device:

struct Pointing_device_interface{ virtual bool onRightClick(Point xy)=0; virtual bool onDoubleClick(Point xy)=0; //.. virtual ~Pointing_device_interface();};

You must declare a virtual destructor for this class because otherwise, the compiler will implicitly declare a non-virtual destructor for it. Here’s the catch: after you declare a destructor (virtual or not), you must define it as well?even if it’s a dummy destructor:


In this example, you’re forced to manually define a dummy destructor simply because it must be virtual. As with the manual definition of a default constructor, a manual destructor?however trivial?is less efficient than an implicitly-defined one, and it imposes an unnecessary burden on the programmer. Ideally, you’d like to have the compiler generate a virtual destructor for you. Let’s see how C++09 defaulted functions get it done:

struct Pointing_device_interface{ virtual int onRightClick(Point xy)=0; virtual int onDoubleClick(Point xy)=0; //.. virtual ~Pointing_device_interface()=default;};

The compiler now implicitly defines a virtual destructor for Pointing_device_interface. The implicitly-defined destructor is as efficient as any implicitly-defined virtual destructor.

Remember, defaulted functions are only declared; you don’t define them. The compiler will automatically define them for you.

A Trivial Question
Defaulted functions solve two problems: they are more efficient than manual implementations and they free the programmer from the burden of defining those functions manually.

C++ makes a distinction between trivial and nontrivial special member functions. This distinction isn’t purely academic; a class that has one or more nontrivial special member functions isn’t a POD type. This raises another question: are defaulted functions trivial?

An inline defaulted function can be trivial. To qualify as trivial, a defaulted function must be identical to the function that the compiler would implicitly declare without the =default specifier. Additionally, the defaulted function must be inline. Consider:

struct S { inline S()=default;};

The defaulted constructor of S is trivial because the compiler would have implicitly-declared a trivial constructor for S by default:

struct S { //no user-declared canonical functions. Hence, S //has implicitly-declared trivial constructor, dtor etc.};

However, the following defaulted destructor isn’t trivial:

struct S { inline virtual ~S()=default;};

The defaulted destructor is inline, which is the first criterion for qualifying as trivial. However, this destructor is virtual, whereas the implicitly-declared destructor would have been non-virtual. Therefore, the defaulted destructor of S is not trivial.

Share the Post:
XDR solutions

The Benefits of Using XDR Solutions

Cybercriminals constantly adapt their strategies, developing newer, more powerful, and intelligent ways to attack your network. Since security professionals must innovate as well, more conventional endpoint detection solutions have evolved

AI is revolutionizing fraud detection

How AI is Revolutionizing Fraud Detection

Artificial intelligence – commonly known as AI – means a form of technology with multiple uses. As a result, it has become extremely valuable to a number of businesses across

AI innovation

Companies Leading AI Innovation in 2023

Artificial intelligence (AI) has been transforming industries and revolutionizing business operations. AI’s potential to enhance efficiency and productivity has become crucial to many businesses. As we move into 2023, several

data fivetran pricing

Fivetran Pricing Explained

One of the biggest trends of the 21st century is the massive surge in analytics. Analytics is the process of utilizing data to drive future decision-making. With so much of

kubernetes logging

Kubernetes Logging: What You Need to Know

Kubernetes from Google is one of the most popular open-source and free container management solutions made to make managing and deploying applications easier. It has a solid architecture that makes

ransomware cyber attack

Why Is Ransomware Such a Major Threat?

One of the most significant cyber threats faced by modern organizations is a ransomware attack. Ransomware attacks have grown in both sophistication and frequency over the past few years, forcing

data dictionary

Tools You Need to Make a Data Dictionary

Data dictionaries are crucial for organizations of all sizes that deal with large amounts of data. they are centralized repositories of all the data in organizations, including metadata such as