7 Features of C++17 that will simplify your code

fenbf
21.8K views

Open Source Your Knowledge, Become a Contributor

Technology knowledge has to be shared and made accessible for free. Join the movement.

Create Content

Template argument deduction for class templates

I have good and bad news for you :)

Do you often use make<T> functions to construct a templated object (like std::make_pair)? With C++17 you can forget about (most of) them and just use regular a constructor :) That also means that a lot of your code - those make<T> functions can now be removed.

The reason?

C++17 filled a gap in the deduction rules for templates. Now the template deduction can happen for standard class templates and not just for functions.

For instance, the following code is (and was) legal:

void f(std::pair<int, char>);

// call:
f(std::make_pair(42, 'z'));

Because std::make_pair is a template function (so we can perform template deduction).

But the following wasn’t (before C++17)

void f(std::pair<int, char>);

// call:
f(std::pair(42, 'z'));

Looks the same, right? This was not OK because std::pair is a template class, and template classes could not apply type deduction in their initialization.

But now we can do that so that the above code will compile under C++17 conformant compiler.

What about creating local variables like tuples or pairs?

std::pair<int, double> p(10, 0.0);
// same as
std::pair p(10, 0.0); // deduced automatically!

Try the code below:

Deduction or tuples and pairs
1
2
3
4
5
6
7
8
9
10
#include <utility>
#include <tuple>
#include <iostream>
int main() {
std::pair d(0, 0.0);
std::tuple t(1, 2, 3);
std::cout << std::get<0>(t) << ", " << std::get<1>(t) << ", " << std::get<2>(t) << "\n";
}
XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX

This can substantially reduce complex constructions like

std::lock_guard<std::shared_timed_mutex, 
        std::shared_lock<std::shared_timed_mutex>> lck(mut_, r1);

Can now become:

std::lock_guard lck(mut_, r1);

Note, that partial deduction cannot happen, you have to specify all the template parameters or none:

std::tuple t(1, 2, 3);              // OK: deduction
std::tuple<int,int,int> t(1, 2, 3); // OK: all arguments are provided
std::tuple<int> t(1, 2, 3);         // Error: partial deduction

Also if you're adventurous you can create your custom class template deduction guides: see here for more information: recent post: Arne Mertz: Modern C++ Features - Class Template Argument Deduction.

BTW: why not all make functions can be removed? For example, consider make_unique or make_shared are they only for 'syntactic sugar' ? I'll leave this as an open question for now.

More details in

MSVC not yet, GCC: 7.0, Clang: not yet.

Open Source Your Knowledge: become a Contributor and help others learn. Create New Content