Common Misconceptions of C++

By Buckaroo - C/C++ Package Manager

“black swirl of letters” by Nathaniel Shuman on Unsplash

C++ has evolved massively in recent years and yet it is still perceived by many as the language that it was back in the early 2000s. Let’s dispel some myths…

C++ is actually growing! Even as computers becomes faster, our demands of what we want to do with them are always increasing. C++ is one of the few languages that allows us to maximize the potential of our hardware.

Stroustrup’s talk from CPP Con shows C++ on a growth trajectory.

With the new auto keyword and lambda syntax, C++ can be correct, fast and concise.

For example, compare these two programs in JavaScript and C++ 14:

JavaScript
C++

Okay, so the C++ one is marginally longer, but think about what you get in return:

  • Strong type system and compile-time type checking
  • No run-time dependency like Node.js
  • Fraction of the execution time

Whilst it is often possible to include C code in C++, this is not always the case. The following snippets are valid C, but not valid C++:

C++ is its own language with its own idioms and best-practices. If you only learn C++ as an extension of C, then you will not learn these patterns and probably write error-prone code!

Kate Gregory did an excellent talk about this that is well worth your time.

How many developers have had a negative experience of C++ because they were taught to use it like C?

C++ allows you to write abstractions that compile-down to equivalent C. This means that with some care, a C++ program will be at least as fast as a C one. The advantage C++ gives over C is that it enables us to also build reusable abstractions with templates, OOP and functional composition.

C++ gives you the tools to encode your intentions in the type-system. This allows the compiler to generate optimal binaries from your code.

C++ the language is completely cross-platform. The reason that many claim C++ is not is that the standard library does not provide that platform abstractions for filesystem, network access and so on that languages like Java do.

Instead, C++ requires you to use a library, or write your own. This might seem painful (although much less so with a package manager!), but it is actually a good thing.

  1. To target a new platform, compiler implementers have less to implement.
  2. Platform targets with limited capabilities can support C++. What would happen if the standard required some feature that a platform cannot provide due to hardware limitations?
  3. You are free to choose the best library for your application. It is not one size fits all.

We covered this is detail in a previous article, but the short version is:

  • apt-get only works on Debian variants
  • apt-get mutates your system, which is inconvenient when switching between projects
  • apt-get is not a good source for new and experimental versions of libraries

In the early days, the big difference between C and C++ was that C++ provides classes. This is still true, but classes are no longer the dominant feature of C++. In modern C++, the focus is on RAII patterns. C++ is not really about classes, it is about deterministic resource management.

The C++ approach to resource management (of which memory is just one kind) is to use RAII patterns rather than a centralized garbage collector.

This is a bit like the “using” pattern seen in other languages. For instance, in C# we might write:

In C++, the disposal should be done by the destructor:

Notice that this is actually less verbose; plus, we can use the same pattern for memory and other resources.

But there is another advantage: the order and timing of object disposal is determined by the scope in which they are used. This makes it possible to control the garbage collection process at a function-level, whereas most garbage-collected languages only allow (limited) control at a global level.

This is an even greater benefit in large projects, since it prevents one module from introducing garbage-collection latency into another. This is the reason C++ is the language of choice for game development and audio processing.

The C++ compilers do an amazing job of optimizing high-level code. This allows you to avoid writing at a low-level, whilst still getting great performance. Sometimes the performance is even better, since the compiler can perform optimizations that would be too tricky to write by hand.

Our favourite example of this is using Conduit, our new C++ sequence library. This program computes the sum of various Fibonacci numbers using lambdas, coroutines and so on:

And yet it compiles to just:

This means the optimizer was able to compute 60 Fibonacci numbers and sum the last 50 at compile-time!

We recently announced BuildInfer, a new tool to optimize your C/C++ build scripts. Take a look!