enum zu string
-
.... schrieb:
Janjan schrieb:
Eine Assertion wäre imho im Default-Zweig deutlich sinnvoller.
default: assert(false);
Aber nicht in der Release.
Im Release würde die Assertion nichts machen, und sowieso sollte dieser Code-Abschnitt niemals im Release erreichbar sein.
-
Janjan schrieb:
.... schrieb:
Janjan schrieb:
Eine Assertion wäre imho im Default-Zweig deutlich sinnvoller.
default: assert(false);
Aber nicht in der Release.
Im Release würde die Assertion nichts machen, und sowieso sollte dieser Code-Abschnitt niemals im Release erreichbar sein.
Hm, ich setze Debugger-Ausgaben oder Asserts ein, je nachdem wie schlimm der Fehler ist. Wenn anschließende Abstürze drohen, dann auf jeden Fall Assert. Kann der Fehler noch ein wenig stehenbleichen, dann Debugger-Ausgabe.
... schrieb:
Ich empfinde diese Variante als wesentlich sinniger:
enum T { A = 0, B, C }; char names[] = { 'A', 'B', 'C' };
Hm, sieht elegant aus, aber die Zuordnung kann leicht mal verloren gehen. Wie wäre es mit folgendem Code.
enum T { A = 0, B, C, last_enum }; char* names[last_enum]; names[A] = "Adam"; names[B] = "Eva"; names[C] = "Schlange"; };
Die Zuordnung bleibt auf jeden Fall erhalten, es kann nichts überlaufen und die Ausgabe ist etwas aussagekräftiger.
tschüß
Troll.Soft
-
Troll.Soft schrieb:
Hm, sieht elegant aus, aber die Zuordnung kann leicht mal verloren gehen. Wie wäre es mit folgendem Code.
enum T { A = 0, B, C, last_enum }; char* names[last_enum]; names[A] = "Adam"; names[B] = "Eva"; names[C] = "Schlange"; };
Die Zuordnung bleibt auf jeden Fall erhalten, es kann nichts überlaufen und die Ausgabe ist etwas aussagekräftiger.
Jopp, da hatte ich auch drüber nachgedacht - aber wie gesagt, da würde man überall code duplizieren...^^
da bräuchte man auch dasA = 0
nicht mehr...bb
-
unskilled schrieb:
da bräuchte man auch das
A = 0
nicht mehr...oops, ist auch nur aus Versehen stehengeblieben.
-
... schrieb:
Ich empfinde diese Variante als wesentlich sinniger:
enum T { A = 0, B, C }; char names[] = { 'A', 'B', 'C' };
Es gibt Situationen, in denen enums nicht lückenlos nummeriert sind und in denen funktionieren solche Varianten nicht.
Wir haben tw. "innere Strukturierungen" in größeren enum-Definitionen (ist nicht schön, aber bisweilen das kleinste Übel). Da ziehen wir dann doch die "switch-Variante" vor - da ist die Verknüpfung einfach direkter.Gruß,
Simon2.
-
Die switch-Variante geht aber halt auch nicht immer...
enum x { A, B, C = A };
Ich weiß zwar nicht mal mehr, wann das bei mir das letzte mal vorkam, aber naja... ^^
Aber stimmt schon, da ist die Troll.Soft-Variante immernoch die tollste...
bb
-
unskilled schrieb:
...
enum x { A, B, C = A };
...
Geht das?
Hätte gedacht, dass da ein Compiler Ärger macht... (und der Standard auch).Gruß,
Simon2.
-
Hat was von deprecated Enum-Einträgen.
Warum keine std::map<EnumTyp, std::string>?
-
Fellhuhn schrieb:
Hat was von deprecated Enum-Einträgen.
Warum keine std::map<EnumTyp, std::string>?
Ist vom Aufwand her auch nicht besser als switch-case.
-
Hm, okay. Sowas? Gerade beim Googlen drüber gestolpert:
#define MY_LIST \ X(foo), \ X(bar), \ X(baz) #define X(x) x enum eMyEnum { MY_LIST }; #undef X #define X(x) #x const char *szMyEnum[] = { MY_LIST }; #undef X
-
unskilled schrieb:
Die switch-Variante geht aber halt auch nicht immer...
enum x { A, B, C = A };
Ich weiß zwar nicht mal mehr, wann das bei mir das letzte mal vorkam, aber naja...
Ich weiß noch genau, wann dieser Fall "C = A" bei mir vorkam. Und das ich ihn nicht gelöst habe. Wenn jemand eine Idee hat, heraus damit.
tschüß
Troll.Soft
-
In solch einem exotischen Fall kann man A und C nicht unterscheiden, denn sie haben einen identischen Wert. Wozu sollte man sie auch unterscheiden sollen? A ist C, und C ist A.
-
Janjan schrieb:
In solch einem exotischen Fall kann man A und C nicht unterscheiden, denn sie haben einen identischen Wert. Wozu sollte man sie auch unterscheiden sollen? A ist C, und C ist A.
Identischer Wert muss nichts heißen. Bei
int a = 0, b = a;
kann ich a und b über &a und &b auch unterscheiden. Bei enum-Werten geht das aber nicht, da sie nur symbolische Kostanten sind und keine Adresse besitzen.
-
ipsec schrieb:
Janjan schrieb:
In solch einem exotischen Fall kann man A und C nicht unterscheiden, denn sie haben einen identischen Wert. Wozu sollte man sie auch unterscheiden sollen? A ist C, und C ist A.
Identischer Wert muss nichts heißen. Bei
int a = 0, b = a;
kann ich a und b über &a und &b auch unterscheiden. Bei enum-Werten geht das aber nicht, da sie nur symbolische Kostanten sind und keine Adresse besitzen.In dem Fall sind a und b aber Unterschiedliche Dinge. Bei A und C vom Enum nicht.
-
Hm, mit variadic macros könnte man was machen, wenn ich nur wüsste wie man bei __VA_ARGS__ aus jedem Element ein String macht wie es bei #element geht... hmm...
-
Vielleicht sollten wir uns darüber unterhalten, welche genauen Anforderungen an die Enumeration gestellt werden. Die fett geschriebenen wurden bisher genannt, ich habe ein paar weitere mögliche aufgelistet:
- Keine Codeduplizierung bei der Definition
- Konvertierbarkeit zu Strings
- Implizite/Explizite Konvertierbarkeit (von und) zu Ganzzahlen
- Compilezeitfehler bei Zugriff auf nicht existenten Enumerator
- Iteration durch alle Enumeratoren
- ...
Je mehr Kriterien erfüllt werden müssen, desto mühsamer wird natürlich eine Implementierung. Praktisch wäre auch ein vollständiges (und dennoch möglichst kleines) Beispiel, welches zeigt, was das
enum
alles leisten soll.
-
Da ist es wohl am einfachsten die gewünschen Enums in einer extra Datei zu verwalten und sich von einem Skript zusammenschustern zu lassen.
-
Toll wäre es, wenn man Enums ähnlich wie in Ada hätte.
Die haben folgende Eigenschaften:
Definitiontype My_Enum is (Red, Green, Blue); --Typdefinition --fuers Hardwarenahe ist das hier toll: for My_Enum'Size use 8; --My_Enum ist 8 Bit gross... for My_Enum'Alignment use 1; --...und wird an 1 Byte Grenzen aligned. for My_Enum use(Red => 1, Green => 2, Blue => 4); --Speicherrepraesentation festlegen
Konvertierbarkeit von Enum zu String und zurück:
Enum : My_Enum := Green; Str : String := My_Enum'Image(Enum); --Str enthaelt String "Green" ... Enum := My_Enum'Value("Red"); --Aus String: Enum jetzt Red
Unerscheidung zwischen interner Repräsentation (numerischer Wert im Speicher) und externer Repräsentation (siehe oben).
Iterierbarkeit über Enumerations:
for E in My_Enum'Range loop --iteriert über alle Elemente im Enum ... end loop;
Arrays von Enums:
type My_Enum_Array is array(My_Enum) of Integer; --Integer Array mit Indizes Red, Green, Blue Array : My_Enum_Array; ... Array(Green) := 10; --geht auch ganz toll mit der Schleife ueber den Range...
Es geht noch mehr, aber das sind die praktischten Eigenschaften.
-
Bleib mir weg mit Ada... so toll manche der Features auch sein mögen, alleine bei den kleinen Schnipseln die du gespostet hast, bekomm ich wieder Kopfschmerzen und Schweißausbrüche.
-
Fellhuhn schrieb:
Bleib mir weg mit Ada... so toll manche der Features auch sein mögen, alleine bei den kleinen Schnipseln die du gespostet hast, bekomm ich wieder Kopfschmerzen und Schweißausbrüche.
Wenn das Forum Syntax-Highlighting für Ada hätte wärs vielleicht besser.
Es geht aber auch eher um die Möglichkeiten, die Enums dort bieten.
Wobei, die Syntax ist anscheinend deutlich Zugänglicher als die von C++. Zumindest kommen Praktikanten, die ich recht häufig betreue, deutlich schneller mit Ada als mit C++ zurecht (sofern sie nicht schon vorbelastet sind).