How to get warning for implicit conversion to lower precision?

If you delete the overload of func that accepts a double argument:

void func(double) = delete;

your user will get a hard error:

func(12.4); // error, user can't choose to ignore it

which is even better than a warning.

Here's a demo.


A deleted primary template with definitions only for specific explicit specializations

If you want to explicitly make sure that there are no unexpected implicit conversions, you could define func as a function template whose primary template definition has been deleted, and where you provide explicit specializations only for the types you want to allow. The deleted primary template will be chosen for types for which there is no exact matching explicit specialization (no implicit conversion in place here).

template<typename T>
void func(T) = delete;

template<>
void func<int>(int) { }

template<>
void func<uint8_t>(uint8_t value) { func<int>(value); }

DEMO.


Deleted and non-deleted overloads depending on type affiliation with a family of types (traits-based using SFINAE)

The approach above, however, would require explicitly typing out an explicit specialization for every single type for which you'd want to allow delegation to some common implementation. This may not be useful unless there is a very small amount of types that should be able to use the overload.

An alternative would be to provide two function template overloads for func, which either has a deleted definition, or a reusable definition, based on a predicate to capture a family of types, e.g. std::is_integral, where each overload leverages SFINAE to be available based on the opposite results of the overload (available for cond or !cond, respectively).

template<typename T,
         typename std::enable_if_t<!std::is_integral_v<T>>* = nullptr>
void func(T) = delete;

template<typename T,
         typename std::enable_if_t<std::is_integral_v<T>>* = nullptr>
void func(T) { }

DEMO

Tags:

C++