Gibt es __CLASS__
in C ++ ein Makro, das den Klassennamen ähnlich dem __FUNCTION__
Makro mit dem Funktionsnamen angibt?
100
Das Nächste, was es gibt, ist anzurufen typeid(your_class).name()
- aber dies erzeugt einen compilerspezifischen verstümmelten Namen.
Um es nur innerhalb der Klasse zu verwenden typeid(*this).name()
__func__
und Nicht-Standard__FUNCTION__
sind keine Makros. Microsoft dokumentiert__FUNCTION__
als Makro, aber das Werbegeschenk, dass es nicht wirklich ist, ist, dass es beim Kompilieren nicht vom Präprozessor erweitert wird/P
.Das Problem bei der Verwendung
typeid(*this).name()
ist, dassthis
ein statischer Methodenaufruf keinen Zeiger enthält. Das Makro__PRETTY_FUNCTION__
meldet einen Klassennamen in statischen Funktionen sowie in Methodenaufrufen. Dies funktioniert jedoch nur mit gcc.Hier ist ein Beispiel für das Extrahieren der Informationen über eine Makroschnittstelle.
Das Makro
__METHOD_NAME__
gibt eine Zeichenfolge des Formulars zurück<class>::<method>()
und schneidet den Rückgabetyp, die Modifikatoren und die Argumente von what ab__PRETTY_FUNCTION__
Sie erhalten.Für etwas, das nur den Klassennamen extrahiert, muss sorgfältig darauf geachtet werden, Situationen abzufangen, in denen es keine Klasse gibt:
quelle
#ifdef __GNU_C__
?substr(0,colons).rfind(" ")
könnte manrfind(' ', colons)
eine Erstellung eines zusätzlichen Strings ersparen.__METHOD_NAME__
Makros geschrieben. Überprüfen Sie hier .constexpr
Funktion zu machen, um es zur Kompilierungszeit auszuwertenIch möchte boost :: typeindex vorschlagen , das ich aus Scott Meyers "Effective Modern C ++" kennengelernt habe. Hier ein grundlegendes Beispiel:
Beispiel
Kompiliert mit "g ++ --std = c ++ 14" ergibt dies Folgendes
Ausgabe
quelle
Noch nicht. (Ich denke
__class__
, irgendwo vorgeschlagen). Sie können auch versuchen, einen Klassenteil aus zu extrahieren__PRETTY_FUNCTION__
.quelle
Ich denke, die Verwendung
__PRETTY_FUNCTION__
ist gut genug, obwohl sie auch einen Namespace enthält, dhnamespace::classname::functionname
bis__CLASS__
verfügbar ist.quelle
Wenn Ihr Compiler zufällig ist
g++
und Sie danach fragen,__CLASS__
weil Sie eine Möglichkeit suchen, den aktuellen Methodennamen einschließlich der Klasse abzurufen ,__PRETTY_FUNCTION__
sollte dies helfen (gemäßinfo gcc
Abschnitt 5.43 Funktionsnamen als Zeichenfolgen ).quelle
Wenn Sie etwas benötigen, das beim Kompilieren tatsächlich den Klassennamen erzeugt, können Sie dazu C ++ 11 verwenden:
Ich erkenne, dass dies nicht dasselbe ist wie,
__FUNCTION__
aber ich habe diesen Beitrag gefunden , als ich nach einer Antwort wie dieser gesucht habe. : D.quelle
Wenn Sie MS C ++ Rede ist (Sie sollten angeben, besonders als
__FUNCTION__
ein Nicht-Standard - Erweiterung ist), gibt es__FUNCDNAME__
und__FUNCSIG__
Symbole , die Sie nicht analysierenquelle
Sie können den Funktionsnamen einschließlich des Klassennamens abrufen. Dies kann C-Typ-Funktionen verarbeiten.
quelle
Meine Lösung:
Ich arbeite für Visual C ++ 12.
quelle
Hier ist eine Lösung, die auf den
__FUNCTION__
Makro- und C ++ - Vorlagen basiert :Hier ist ein Beispiel, wie dies für eine Logger-Klasse verwendet werden kann
Die Ausgabe von
Example::Run
wird dann seinquelle
Dies funktioniert ganz gut, wenn Sie bereit sind, die Kosten für einen Zeiger zu bezahlen.
quelle
Funktioniert auch mit msvc und gcc
quelle
Alle oben aufgeführten Lösungen, die sich auf
__PRETTY_FUNCTION__
do stützen , haben bestimmte Randfälle, in denen sie nicht nur den Klassennamen / Klassennamen zurückgeben. Betrachten Sie zum Beispiel den folgenden hübschen Funktionswert:Die Verwendung des letzten Vorkommens
"::"
als Trennzeichen funktioniert nicht, da der Funktionsparameter auch ein"::"
(std::string
) enthält . Sie können ähnliche Randfälle"("
als Trennzeichen und mehr finden. Die einzige Lösung, die ich gefunden habe, verwendet sowohl das__FUNCTION__
als auch das__PRETTY_FUNCTION__
Makro als Parameter. Hier ist der vollständige Code:quelle
Die folgende Methode (basierend auf methodName () oben) kann auch Eingaben wie "int main (int argc, char ** argv)" verarbeiten:
quelle