Ich habe eine Enum-Klasse mit zwei Werten und möchte eine Methode erstellen, die einen Wert empfängt und den anderen zurückgibt. Ich möchte auch die Typensicherheit gewährleisten (deshalb verwende ich die Aufzählungsklasse anstelle von Aufzählungen).
http://www.cplusplus.com/doc/tutorial/other_data_types/ erwähnt nichts über Methoden Ich hatte jedoch den Eindruck, dass jede Art von Klasse Methoden haben kann.
enum class/struct
bestätigt?Antworten:
Nein, das können sie nicht.
Ich kann verstehen, dass der
enum class
Teil für stark typisierte Aufzählungen in C ++ 11 möglicherweise impliziert, dass Sieenum
auchclass
Merkmale haben, aber das ist nicht der Fall. Meine Vermutung ist, dass die Auswahl der Schlüsselwörter von dem Muster inspiriert wurde, das wir vor C ++ 11 verwendet haben, um Aufzählungen mit Gültigkeitsbereich zu erhalten:Das ist jedoch nur Syntax. Auch hier
enum class
ist keinclass
.quelle
union
ist nicht das, was John Doe auch als Klasse betrachten würde. Sie können jedoch Mitgliedsfunktionen haben. Und Klassen sind für Mitgliedsfunktionen wirklich nicht obligatorisch. Die Verwendung eines Bezeichners wievalue
oderthis
, so etwas wieenum Size { Huge, Mega, Apocalypse; bool operator<(X rhs) const { return *this < rhs; }
(hier auch zulässig;
), kann genauso sinnvoll sein wie andere Arten von Funktionen.Obwohl die Antwort "Sie können nicht" technisch korrekt ist, glaube ich, dass Sie möglicherweise das gewünschte Verhalten mit der folgenden Idee erreichen können:
Ich stelle mir vor, dass Sie etwas schreiben möchten wie:
Und Sie hatten gehofft, dass der Code ungefähr so aussieht:
Aber natürlich funktioniert es nicht, weil Enums keine Methoden haben können (und 'das' bedeutet im obigen Kontext nichts)
Wenn Sie jedoch die Idee einer normalen Klasse verwenden, die eine Aufzählung außerhalb der Klasse und eine einzelne Elementvariable enthält, die einen Wert dieses Typs enthält, können Sie der gewünschten Syntax / Verhalten / Typensicherheit sehr nahe kommen. dh:
Jetzt können Sie schreiben:
Und der Compiler verhindert Dinge wie:
Sie können leicht Methoden hinzufügen, die:
und
kann unterstützt werden.
quelle
Eine mögliche Antwort ist die Konzentration auf die Beschreibung der Frage anstelle des Titels
quelle
Wie in der anderen Antwort erwähnt , nein. Auch
enum class
ist keine Klasse.Normalerweise ist die Notwendigkeit haben Methoden für eine
enum
ergibt sich aus dem Grund , dass es nicht eine regelmäßige (nur Inkrementieren) Enum, aber irgendwie bitweise Definition von Werten maskiert werden oder müssen andere Bit-Rechenoperationen:Offensichtlich denkt man daran, die notwendigen Operationen zum Zurücksetzen / Zurücksetzen einer einzelnen / Gruppe von Bits zu kapseln, beispielsweise durch einen Bitmaskenwert oder sogar durch bitindexgesteuerte Operationen, die zur Manipulation eines solchen Satzes von "Flags" nützlich wären.
Das c ++ 11
struct
/class
specation unterstützt nur ein besseres Scoping der Enum-Werte für den Zugriff. Nicht mehr und nicht weniger!Um aus der Einschränkung herauszukommen, können Sie keine Methoden für enum (Klassen) deklarieren , indem Sie entweder eine
std::bitset
(Wrapper-Klasse) oder ein Bitfeld verwendenunion
.union
s, und solche Bitfeld-Gewerkschaften können Methoden haben (siehe hier für die Einschränkungen!).Ich habe ein Beispiel, wie Bitmaskenwerte (wie oben gezeigt) in ihre entsprechenden Bitindizes konvertiert werden, die hier verwendet
std::bitset
werden können: BitIndexConverter.hppIch fand dies ziemlich nützlich, um die Lesbarkeit einiger ' Flag'-Entscheidungen zu verbessern Algorithmen.
quelle
Es gibt eine ziemlich kompatible Fähigkeit (§), eine Aufzählung in eine Klasse umzuwandeln, ohne Ihren Code neu schreiben zu müssen, was bedeutet, dass Sie effektiv das tun können , was Sie wollten, ohne zu viel zu bearbeiten.
(§) Wie ElementW in einem Kommentar hervorhebt , funktioniert type_traits- abhängiger Code nicht, z. B. kann man nicht auto usw. verwenden. Es kann eine Möglichkeit geben, mit solchen Dingen umzugehen , aber am Ende konvertiert man eine Aufzählung in eine Klasse. und es ist immer ein Fehler, C ++ zu untergraben
Die
enum struct
undenum class
Spezifikationen beziehen sich auf das Scoping, sind also nicht Teil davon.Ihre ursprüngliche Aufzählung ist zB "Haustier" (dies ist nur ein Beispiel!).
(1) Sie ändern dies in zB petEnum (um es vor Ihrem vorhandenen Code zu verbergen).
(2) Sie fügen darunter eine neue Klassendeklaration hinzu (benannt mit der ursprünglichen Aufzählung).
(3) Sie können Ihrer Haustierklasse jetzt beliebige Klassenmethoden hinzufügen. z.B. ein String-Operator
Jetzt können Sie zB std :: cout verwenden ...
quelle
pet
Typabzug verwenden , bei dem ein Typname / eine Instanz erwartet wird , seien es Vorlagenauto
oderdecltype
dies bricht ab, wenn SiepetEnum
stattdessen eine erhalten.Es erfüllt möglicherweise nicht alle Ihre Anforderungen, aber mit Betreibern, die keine Mitglieder sind, können Sie trotzdem viel Spaß haben. Beispielsweise:
Dies ermöglicht Code wie
quelle