For example, I've got this:
// Code A
int create_int() { return 42; }
double create_double() { return 3.14; }
std::string create_string() { return {"Hi"}; }
Now let's assume that it makes sense to put these create
s together, so I rewrite the code:
// Code B
template <typename T> T create();
template <> int create<int>() { return 42; }
template <> double create<double>() { return 3.14; }
template <> std::string create<std::string>() { return {"Hi"}; }
Or even:
// Code C
#include <type_traits>
template <typename T> T create()
{
if constexpr (std::is_same_v<T, int>)
{
return 42;
}
else if constexpr (std::is_same_v<T, double>)
{
return 3.14;
}
else if constexpr (std::is_same_v<T, std::string>)
{
return {"Hi"};
}
else
{
// static_assert(false);
return static_cast<T>(0);
}
}
I wanna to know is there any difference between these codes, or is it just about code style.
There are semantic differences between these. You can't use the Code A
functions in generic algorithms like in this example:
template <class T>
T generic_function() {
return create<T>();
}
Therefore I would prefere Code B over Code A.
The constexpr if is useful if you need to take a different route in generic algorithms. It saves you from creating an overloaded helper function or worse constructs.
An example would be to take a different route for void
over other datatypes because you can not pass void
as a parameter to a function. Suppose you take a function and want to set the value of a std::promise
to the result. This function might not return a value, but you still want to execute the function. In this case the constexpr if
will save you from a lot of headache and template metaprogramming.
template <class Fn>
void my_function(Fn fn) {
std::promise<decltype(fn())> promise;
if constexpr(!std::is_same_v<void, decltype(fn())>) {
promise.set_value(fn());
} else {
fn();
promise.set_value();
}
}
It depends on your use case. if constexpr
is limited to function scope, meaning you can't define your create
function for Foo
in foo.h
and Bar
in bar.h
, so you have to include both.
This is not a criticism of if constexpr
, as it is incredible useful in keeping related generic code brief and in one place.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.