SFINAE mit friend class [Erledigt]
-
Hallo,
ich will mit SFINAE überprüfen, ob eine Klasse eine gewisse Methode hat.
Mein Problem ist, dass das nur funktioniert, wenn die Methode public ist. Wenn sie private ist, dann geht das nicht, obwohl die Klasse, die das überprüft eine Friend-Klasse ist.
Mache ich etwas falsch oder geht das tatsächlich nicht?Hier mein Code:
#include <iostream> #include <type_traits> /// Check if service supports config storage template <typename Service> std::true_type supportsConfigStorage_(decltype(&Service::setConfigStorage)); template <typename Service> std::false_type supportsConfigStorage_(...); template <typename Service> constexpr bool supportsConfigStorage = decltype(supportsConfigStorage_<Service>(nullptr))::value; class Checker; struct Foo { void setConfigStorage() {} }; struct Bar { private: friend class Checker; void setConfigStorage() {} }; struct Checker { template<typename T> void print() { if constexpr (supportsConfigStorage<T>) { std::cout<<"Has config storage" << std::endl; } else { std::cout<<"Has NO config storage" << std::endl; } } }; int main() { Checker checker; checker.print<Foo>(); // "Has config storage" checker.print<Bar>(); // "Has NO config storage" return 0; }
Hier kann man rumspielen.
Danke im Voraus!
Steffo
-
Es ist ja nicht
Checker
, das die "Prüfung" unternimmt, sondernsupportsConfigStorage_
. Das Freundschaftverhältnis zuChecker
ist daher unerheblich für den Wert vonsupportsConfigStorage_
. Wenn dusupportsConfigStorage_
zum Friend machst, bekommst du tatsächlich "Has config storage". Aber das sagt dir dann wieder nichts darüber, obsetConfigStorage
fürChecker
sichtbar ist - das Ergebnis ist das gleiche ob mit oder ohne Zeile 22.PS: Da die template-friend-Deklaration nicht so offensichtlich ist, sie sollte lauten:
struct Bar { private: // friend class Checker; // Ist jetzt egal ob friend oder nicht template<class Service> friend std::true_type supportsConfigStorage_(decltype(&Service::setConfigStorage)); void setConfigStorage() {} };
-
@SeppJ Oha! Das hat mir weitergeholfen! Ich hatte da einen Denkfehler, da im Produktiv-Code der
Checker
auch diesetConfigStorage()
-Methode aufruft und da brauchte ich auf jeden Fall denChecker
als Friend-Class, aber in dem Fall auch zusätzlich die Template-Methode, da sie ja die Überprüfung macht!Danke!!!