Scott Meyers opublikował treść i status swojej następnej książki EC ++ 11. Napisał, że jedną z pozycji w książce może być „Unikaj std::enable_if
w sygnaturach funkcji” .
std::enable_if
może być używany jako argument funkcji, jako typ zwracany lub jako szablon klasy lub parametr szablonu funkcji do warunkowego usuwania funkcji lub klas z rozpoznawania przeciążenia.
W tym pytaniu pokazane są wszystkie trzy rozwiązania.
Jako parametr funkcji:
template<typename T>
struct Check1
{
template<typename U = T>
U read(typename std::enable_if<
std::is_same<U, int>::value >::type* = 0) { return 42; }
template<typename U = T>
U read(typename std::enable_if<
std::is_same<U, double>::value >::type* = 0) { return 3.14; }
};
Jako parametr szablonu:
template<typename T>
struct Check2
{
template<typename U = T, typename std::enable_if<
std::is_same<U, int>::value, int>::type = 0>
U read() { return 42; }
template<typename U = T, typename std::enable_if<
std::is_same<U, double>::value, int>::type = 0>
U read() { return 3.14; }
};
Jako typ zwrotny:
template<typename T>
struct Check3
{
template<typename U = T>
typename std::enable_if<std::is_same<U, int>::value, U>::type read() {
return 42;
}
template<typename U = T>
typename std::enable_if<std::is_same<U, double>::value, U>::type read() {
return 3.14;
}
};
- Które rozwiązanie powinno być preferowane i dlaczego powinienem unikać innych?
- W jakich przypadkach „Unikaj
std::enable_if
w sygnaturach funkcji” dotyczy użycia jako typu zwracanego (co nie jest częścią normalnej sygnatury funkcji, ale specjalizacji szablonów)? - Czy są jakieś różnice w szablonach funkcji składowych i niebędących członkami?
std::enable_if
zaśmiecać moich sygnatur funkcji (zwłaszcza brzydkiej nullptr
wersji argumentu funkcji dodatkowej ), ponieważ zawsze wygląda na to, co to jest, dziwny hack (coś static if
może zrobić dużo piękniejsze i bardziej przejrzyste), używając czarnej magii szablonów, aby wykorzystać ciekawą funkcję języka. Dlatego wolę wysyłanie tagów, gdy tylko jest to możliwe (cóż, nadal masz dodatkowe dziwne argumenty, ale nie w interfejsie publicznym, a także znacznie mniej brzydkie i tajemnicze ).
=0
w tym stanie typename std::enable_if<std::is_same<U, int>::value, int>::type = 0
? Nie mogłem znaleźć odpowiednich zasobów, aby to zrozumieć. Wiem, że pierwsza część =0
ma typ członka, int
jeśli U
i int
jest taki sam. Wielkie dzięki!