Gibt es eine Möglichkeit, in C ++ 11 zu überprüfen, ob eine Aufzählung fortlaufend ist ?
Es ist voll gültig, eine Aufzählung anzugeben, die nicht sind. Gibt es möglicherweise eine Funktion wie ein Typmerkmal in C ++ 14, C ++ 17 oder C ++ 20, um zu überprüfen, ob die Aufzählung fortlaufend ist? Dies soll in einem static_assert verwendet werden.
Es folgt ein kleines Beispiel:
enum class Types_Discontinuous {
A = 10,
B = 1,
C = 100
};
enum class Types_Continuous {
A = 0,
B = 1,
C = 2
};
static_assert(SOME_TEST<Types_Discontinuous>::value, "Enum should be continuous"); // Fails
static_assert(SOME_TEST<Types_Continuous>::value, "Enum should be continuous"); // Passes
enum
. Leider habe ich einen Tagesjob und kann daher nicht versuchen, dies aufzuschreiben, obwohl ich eine Antwort auf der Grundlage dieses Ansatzes positiv bewerten werde. Ich bin mir ziemlich sicher, dass jemand wie @barry oder @sehe das könnte.static_assert
)? Auch wenn Sie keine "schöne Lösung" finden können, schreiben Sie bitte trotzdem eine Antwort, da ich sehr gespannt bin, wie dies generisch gemacht werden könnte.Antworten:
Für eine Reihe von
enum
s können Sie sich wahrscheinlich mithilfe der Magic Enum- Bibliothek durch diese Sache hacken . Zum Beispiel:Beachten Sie, dass dies tatsächlich, wie der Name der Bibliothek andeutet, "Magie" ist - die Bibliothek funktioniert bei einer Reihe von compilerspezifischen Hacks. Als solches erfüllt es nicht wirklich Ihre Anforderungen an "reines C ++", ist aber wahrscheinlich so gut wie möglich, bis wir Reflexionsmöglichkeiten in der Sprache haben.
quelle
Dies ist in reinem C ++ nicht möglich, da es keine Möglichkeit gibt, die Aufzählungswerte aufzulisten oder die Anzahl der Werte sowie die Minimal- und Maximalwerte zu ermitteln. Sie können jedoch versuchen, mithilfe Ihres Compilers etwas zu implementieren, das Ihren Wünschen entspricht. In gcc ist es beispielsweise möglich, einen Kompilierungsfehler zu erzwingen, wenn eine
switch
Anweisung nicht alle Werte einer Aufzählung verarbeitet:Dies ist natürlich auf eine bestimmte Aufzählung spezialisiert, aber die Definition solcher Funktionen kann mit einem Präprozessor automatisiert werden.
quelle
Ich würde gerne eine Antwort darauf sehen. Ich habe es auch gebraucht.
Leider glaube ich nicht, dass dies mit den vorhandenen Dienstprogrammen möglich ist. Wenn Sie hierfür ein Typmerkmal implementieren möchten, benötigen Sie Unterstützung von Ihrem Compiler, sodass das Schreiben einer Vorlage dafür nicht möglich klingt.
Ich habe die Aufzählung bereits um ein bestimmtes Tag erweitert, um anzuzeigen, dass sie zusammenhängend ist, und gibt Ihnen sofort die Größe: Enum-Klassenkonstruktor c ++, wie kann ein bestimmter Wert übergeben werden?
Alternativ können Sie Ihr eigenes Merkmal schreiben:
Dies muss immer dann spezialisiert werden, wenn Sie eine zusammenhängende Aufzählung definieren, in der Sie diese verwenden möchten. Leider erfordert dies einige Wartung und Aufmerksamkeit, wenn die Aufzählung geändert wird.
quelle
Alle Aufzählungen sind fortlaufend. 0 ist immer erlaubt; Der höchste zulässige Wert ist der höchste auf den nächsten aufgerundete Enumerator
1<<N -1
(alle Bits eins), und alle dazwischen liegenden Werte sind ebenfalls zulässig. ([dcl.enum] 9.7.1 / 5). Wenn negative Enumeratoren definiert sind, wird der niedrigste zulässige Wert auf ähnliche Weise definiert, indem der niedrigste Enumerator abgerundet wird.Die in definierten Enumeratoren
enum
sind konstante Ausdrücke mit einem Wert im Bereich und dem richtigen Typ. Sie können jedoch zusätzliche Konstanten außerhalb der definieren,enum
die dieselben Eigenschaften haben:constexpr enum class Types_Discontinuous = static_cast<Types_Discontinuous>(2)
quelle