substitution failure is not an error
Főnév
substitution failure is not an error (tsz. substitution failure is not an errors)
- (informatika) SFINAE (Substitution Failure Is Not An Error) egy haladó C++ sablonmechanizmus, ami lehetővé teszi, hogy a sablonpéldányosítás során keletkező típushelyettesítési hibák ne okozzanak fordítási hibát, hanem a fordító egyszerűen kizárja a nem illeszkedő sablont a lehetséges opciók közül.
🧠 Lényege
Amikor egy sablonfüggvény vagy sablonosztály példányosítása során a típusparaméterek behelyettesítésekor fordítási hiba keletkezne, a fordító nem dob hibát, hanem kihagyja ezt a verziót a túlterhelésből. Így a fordító másik overload-ot keres helyette.
🔧 Egyszerű példa
template<typename T>
void printIfIntegral(T value) {
static_assert(std::is_integral<T>::value, "T must be an integral type");
std::cout << "Egész szám: " << value << std::endl;
}
Ez fordítási hibát dob, ha T nem egész szám.
De:
template<typename T>
typename std::enable_if<std::is_integral<T>::value>::type
printIfIntegral(T value) {
std::cout << "Egész szám: " << value << std::endl;
}
Ez a változat csak akkor fordul le, ha T egy int, char, long, stb. – vagyis std::is_integral<T>::value == true.
Ha nem az, a sablon példányosítása meghiúsul – de nem hiba! A fordító egyszerűen tovább keres másik overload-ot.
🧪 Konkrét példa túlterheléssel
#include <iostream>
#include <type_traits>
template<typename T>
typename std::enable_if<std::is_integral<T>::value>::type
foo(T x) {
std::cout << "Egész típus" << std::endl;
}
template<typename T>
typename std::enable_if<std::is_floating_point<T>::value>::type
foo(T x) {
std::cout << "Lebegőpontos típus" << std::endl;
}
Használat:
foo(42); // Egész típus
foo(3.14); // Lebegőpontos típus
A fordító az enable_if segítségével kizárja azt a verziót, ami nem alkalmazható – ez a SFINAE működése.
📜 enable_if röviden
template<bool B, typename T = void>
struct enable_if {};
template<typename T>
struct enable_if<true, T> { using type = T; };
Tehát ha a feltétel igaz, akkor van ::type, különben nincs → a típushelyettesítés meghiúsul.
🔎 SFINAE alkalmazási területek
- Overload kiválasztás típus alapján
- Kompiláció idejű feltételes aktiválás
- Sablongenerikus kód testreszabása
- STL belső működés (pl.
std::vectorkonstruktora)
🛑 Mikor nem működik?
SFINAE csak sablonpéldányosítás során működik. Ha a hiba nem a példányosításkor, hanem az általános sablon definícióban van (pl. szintaktikai hiba), akkor az valódi hiba lesz.
🧰 Modern C++ rövidítés (C++14, C++17)
Függvény sablon rövidítés (C++14):
template<typename T>
std::enable_if_t<std::is_integral_v<T>>
foo(T x) {
std::cout << "Integral" << std::endl;
}
enable_if_t= rövidítéstypename std::enable_if<...>::typeis_integral_v<T>= rövidítésstd::is_integral<T>::value
🔄 Alternatíva: if constexpr (C++17-től)
template<typename T>
void foo(T x) {
if constexpr (std::is_integral_v<T>) {
std::cout << "Egész szám" << std::endl;
} else {
std::cout << "Nem egész szám" << std::endl;
}
}
Ez nem SFINAE, hanem kompiláció idejű feltételes ágak – de sok esetben könnyebben olvasható és fenntartható.
🧩 Összefoglalás
| Fogalom | Jelentés |
|---|---|
| SFINAE | A sablonpéldányosítás során fellépő típushelyettesítési hibák nem dobják meg a fordítót, csak kizárják a sablont |
| Eszköz | std::enable_if, std::is_integral, decltype, sizeof, stb. |
| Használat | Overload kiválasztás, kompiláció idejű viselkedés módosítás |
| Alternatíva | if constexpr C++17-től, koncepciók (concepts) C++20-tól |
- substitution failure is not an error - Szótár.net (en-hu)
- substitution failure is not an error - Sztaki (en-hu)
- substitution failure is not an error - Merriam–Webster
- substitution failure is not an error - Cambridge
- substitution failure is not an error - WordNet
- substitution failure is not an error - Яндекс (en-ru)
- substitution failure is not an error - Google (en-hu)
- substitution failure is not an error - Wikidata
- substitution failure is not an error - Wikipédia (angol)