Type-Traits (Correctness and Optimization)
Explore how type-traits in C++ ensure type safety and optimize generic algorithms. Learn to use std::is_integral, std::conditional, std::common_type, and std::enable_if to refine templates for correctness and performance.
Correctness
The reason we use type-traits is correctness and optimization. Let’s start with correctness. The idea is to implement generic gcd algorithms, step by step, to make it more type-safe with the help of the type-traits library.
gcd - The First
Our starting point is the euclid algorithm to calculate the greatest common divisor of two numbers.
It’s quite easy to implement the algorithm as a function template and feed it with various arguments. Let’s start!
The function template has two serious issues.
- First, it is too generic. The function template accepts doubles (line 13) and C strings (line 14). But it makes no sense to determine the greatest common divisor of both data types. The modulo operation (
%) for the double and the C string values fails in line 6. But that’s not the only issue. - Second, gcds depend on one type parameter,
T. This shows the function template signaturegcd(T a, T b)).aandbhave to be of the same typeT. There is no conversion for type parameters. Therefore, the instantiation of gcd with an int type and a long type (line 15) fails.
gcd - The Second
We can ignore the rest of the examples below where both arguments have to be positive numbers. The static_assert operator and the predicate std::is_integral<T>::value will help us to check at compile-time whether T is an integral type. A predicate always returns a boolean value.
Great. We have solved the first issue of the gcd algorithm. The compilation will not fail by accident because the modulo operator is not defined for a double value and a C string. The compilation fails because the assertion in line 6 will not hold true. The subtle difference is that we now get an exact error message and not a cryptic output of a failed template instantiation as in the first example.
But what about ...