C++ Core Guidelines: Naming and Layout Rules

The C++ core guidelines have about twenty naming and layout rules. A few of them are obvious; a few of them may be controversial. Let's see, what I mean.

Naming and Layout Rules

First of all, consistency is more important than these naming and layout rules. With this in mind, here is an overview of the rules.

  • NL.1: Don’t say in comments what can be clearly stated in code
  • NL.2: State intent in comments
  • NL.3: Keep comments crisp
  • NL.4: Maintain a consistent indentation style
  • NL.5: Don’t encode type information in names
  • NL.7: Make the length of a name roughly proportional to the length of its scope
  • NL.8: Use a consistent naming style
  • NL.9: Use ALL_CAPS for macro names only
  • NL.10: Avoid CamelCase
  • NL.11: Make literals readable
  • NL.15: Use spaces sparingly
  • NL.16: Use a conventional class member declaration order
  • NL.17: Use K&R-derived layout
  • NL.18: Use C++-style declarator layout
  • NL.19: Avoid names that are easily misread
  • NL.20: Don’t place two statements on the same line
  • NL.21: Declare one name (only) per declaration
  • NL.25: Don’t use void as an argument type
  • NL.26: Use conventional const notation

I will not write about the naming and layout rules of the C++ core guidelines which have already sufficient explanations. I only write about the rules, which need additional wording or are often discussed in my seminars.

Honestly, I'm not a friend of writing a comment to each piece of code. Commenting each piece of code may be a code smell because you code it too sophisticated. I'm more with the Python rule: explicit is better than implicit. I only write a comment if I have to apply a trick which is not apparent. For example, young professionals tend to remove curly braces from your code such as you would remove redundant round braces from an arithmetic expression. If you don't believe me, visit my seminars. But curly braces are essential to scopeRAII objects such as locks or smart pointers. Removing a curly brace from a lock may give you a slower program, or a deadlock. On end, a lot of my customers comment the following usage of curly braces.

std::mutex mut;
{   // necessary to manage the lifetime of the lock
    std::lock_guard<std::mutex> lock(mut);
    ...
}

What is bad about comments is that they become out of date. By definition, this is not possible for the source code. It's always up to date.  As a freshman, my job was quite often to refactor legacy code. Honestly, I had often no clue what it does, and I was, therefore, quite frustrated. To my rescue, I found a few comments. But the comments were completely out-dated. It took me quite a time to recognise this, and you can't image how I felt. Comments have to be maintained as code but are often very sloppy maintained.

NL.5: Don’t encode type information in names

Really? I thought since the last millennium we are done with Hungarian Notation. I mean this good old times in which our variables had no type. Hungarian Notation  is redundant with the type-checking of the compiler, contradicts generic programming, and - this is my main arguments - becomes out-dated as comments become out-dated. Can you guess for what the following variable names stand?

bBusy;
fBusy;
pFoo;
szLastName;
fnFunction;
pszOwner;
rgfpBalances;
lpszBar;
g_nWhells;
m_whells;
_whells;

If you don't know, here it the solution: Hungarian Notation.

NL.7: Make the length of a name roughly proportional to the length of its scope

This rule sounds strange, but we are already used to it. Giving a variable the name i or j, or giving a variable the name T will make the intention of the code immediately clear: i and j are indices, and T is a type parameter of a template.

template<typename T>    
void print(ostream& os, const vector<T>& v)
{
    for (int i = 0; i < v.size(); ++i)
        os << v[i] << '\n';
}

There is a meta-rule behind this rule. A name should be self-explanatory. In a short context, you get with a glance what the variable means. This self-evidence will not automatically hold for longer contexts; therefore, you should use longer names.

NL.16: Use a conventional class member declaration order

Okay, this is an easy but quite helpful rule.

  • When you declare a class, use the following order: constructors, assignments, destructor before functions, and data.
  • The same goes for public, protected, and private: Use the public before protected before private order.
  • Don't use the access specifiers in a class more than once:
class X {   // bad
public:
    void f();
public:
    int g();
    // ...
};

NL.19: Avoid names that are easily misread

Can you read this example without any hesitation?

if (readable(i1 + l1 + ol + o1 + o0 + ol + o1 + I0 + l0)) surprise();

Honestly, I often have issues when I type-in a password having the number 0, or the big capital O. Two years ago it took me quite a time to log into a server. The automatically generated password had a character O.

NL.20: Don’t place two statements on the same line

Let me give you two examples. Did you spot the two issues?

char* p, p2;
char a = 'a';
p = &a;
p2 = a;                              // (1)

int a = 7, b = 9, c, d = 10, e = 3;  // (2)

p2 is a char  (1), and c is not initialised (2).

With C++17, we got an exception to this rule: structured binding. Structured binding allows me to declare more than one name in one declaration (line 1).

Now, I can write the if statement with an initialiser cleaner and more readable.

std::map<int,std::string> myMap;

if (auto [iter, succeeded] = myMap.insert(value); succedded){  // (1)
    useResult(iter);  
    // ...
} 
else{
    // ...
} // iter and succeeded are automatically destroyed            

What's next?

DONE! After more than one hundred posts to theC++ core guidelines, I have two good news for you.

First, I write a book about the C++ core guidelines, in which I try my best to make a readable and concise story out of this highly valuable content. My idea is it, to base my story on C++17 and these rules of the C++ core guidelines, which are essential to write modern C++. Of course, modern C++ means, in particular, to write type-safe, bounds safe, and lifetime safe C++ code. So, stay tuned, I start in the next days and give you an update, if appropriate.

Second, my blog will shift to the hot topic in C++: the upcoming C++20 standard. My posts start in a breadth-first search and will end in a depth-first search. C++20 is presumably as powerful as C++11. You can, therefore, assume, that I have a lot to write.

Thanks a lot to my Patreon Supporters : Paul Baxter,  Meeting C++, Matt Braun, Roman Postanciuc, Venkata Ramesh Gudpati, Tobias Zindl, Marko, G Prvulovic, Reiner Eiteljörge, Benjamin Huth, Reinhold Dröge, Abernitzke, Richard Ohnemus , Frank Grimm , Sakib, Broeserl, and António Pina.  

Thanks in particular to:

Get your e-book at Leanpub:

The C++ Standard Library

Concurrency With Modern C++

Get Both as one Bundle

With C++11, C++14, and C++17 we got a lot of new C++ libraries. In addition, the existing ones are greatly improved. The key idea of my book is to give you the necessary information to the current C++ libraries in about 200 pages.

C++11is the first C++ standard that deals with concurrency. The story goes on with C++17 and will continue with C++20 .

I'll give you a detailed insight in the current and the upcoming concurrency in C++. This insight includes the theory and a lot of practice with more the 100 source files.

Get my books " The C++ Standard Library " (including C++17) and " Concurrency with Modern C++ " in a bundle.

In sum, you get more than 600 pages full of modern C++ and more than 100 source files presenting concurrency in practice.

Get your interactive course

Modern C++ Concurrency in Practice

C++ Standard Library including C++14 & C++17

Based on my book "Concurrency with Modern C++" educative.io created an interactive course.

What's Inside?

  • 140 lessons
  • 110 code playgrounds => Runs in the browser
  • 78 code snippets
  • 55 illustrations

Based on my book "The C++ Standard Library" educative.io created an interactive course.

What's Inside?

  • 149 lessons
  • 111 code playgrounds => Runs in the browser
  • 164 code snippets
  • 25 illustrations
我来评几句
登录后评论

已发表评论数()

相关站点

+订阅
热门文章