Moin Leute, der Zeit schreibe ich an einem Programm, das in der Grundstruktur ein endlicher Automat mit 8 Zuständen ist. Die Zustände werden durch 3 Faktoren beschrieben: Editiermodus (Ja/Nein), Optionsmenü aktiv (Ja/Nein), Cursorposition (0,1,2). Diese habe ich wie folgt definiert: enum editierbar {NO_EDIT=0, EDIT}; enum optdialog {NO_OPTION=0, OPTION}; enum postion {POS1=0, POS2, POS3}; Diese Faktoren haben ich in einem struct zusammengefasst. typedef struct { enum editierbar edit; enum optdialog opt; enum postion pos; }status; Diese Definitionen stehen in der Header-Datei. Im Main deklariere und initialisiere ich die Variable "zustand": status zustand={NO_EDIT,NO_OPTION,POS1}; Mein Ziel ist es, das ich ein Switch nutze wie folgt: switch (zustand.edit|zustand.opt|zustand.pos) { case NO_EDIT|NO_OPTION|POS1: usw... leider funktioniert dies nicht wie gewünscht. Der Compiler berichtet, dass die folgenden Cases schon definiert wurden. Bisher habe ich im Web keine Ansätze für eine ähnliche Umsetzung in C gefunden. Kann C (WinAVR) eine solche Lösung abbilden? Vielen Dank für eure Hilfe! Gruß, Christian.
#define X(e,o,p) ((e)<<4|(o)<<2|(p)) switch (X(zustand.edit,zustand.opt,zustand.pos)) { case X(NO_EDIT|NO_OPTION|POS1): ...
Hi! der ausdruck "NO_EDIT|NO_OPTION|POS1" ist ein binäres oder aus den 3 enums, und hat damit den wert 1 egal ob es nun EDIT oder NO_EDIT heißt. Folglich bekommst du doppelte Cases :-) eine lösung wäre: temp= status.edit + status.opt<<1 + status.pos<<2; switch (temp) { case (NO_EDIT + NO_OPTION<<1 + POS1<<2): ... } Alternativ: kannst du die shifterei gleich in die Enums ziehen: enum editierbar {NO_EDIT=0, EDIT=1}; enum optdialog {NO_OPTION=0, OPTION=2}; enum postion {POS1=0, POS2=4, POS3=8}; und sonst bei deinem code bleiben.
Andreas R. wrote:
> temp= status.edit + status.opt<<1 + status.pos<<2;
Guck dir das Kapitel über die Operator-Prioriäten lieber noch mal an.
Mit "|" funktioniert das so, mit "+" nicht.
A. K. wrote: > #define X(e,o,p) ((e)<<4|(o)<<2|(p)) > > switch (X(zustand.edit,zustand.opt,zustand.pos)) { > case X(NO_EDIT|NO_OPTION|POS1): > ... Moin! Vielen Dank für eure schnellen Antworten. Ich habe die oben zitierte Implementierung umgesetzt und meinen Code um diesen erweitert. Hat super geklappt, mit der Modifikation, nur musste ich statt case X(NO_EDIT|NO_OPTION|POS1): das schreiben: case X(NO_EDIT,NO_OPTION,POS1): Läuft super rund. Ich probiere den Ansatz noch mal etwas zu beschreiben, wie ich ihn verstanden habe, damit die Lösung ggf. auch von anderen leichter zu finden ist. Durch das "#define X(e,o,p) ((e)<<4|(o)<<2|(p))" wird X mit 3 Parametern definiert, die je nach Stelle um 4 bzw. 2 Bit nach Links verschoben werden, so das man in X, alle 3 Faktoren kodiert in einem Wert. Auf diesen nun einen Wert kann man leicht ein Switch laufen lassen. Vielen Dank noch mal! Gruß, Christian
Christian Blank wrote: > case X(NO_EDIT|NO_OPTION|POS1): > das schreiben: > case X(NO_EDIT,NO_OPTION,POS1): Yep, sorry. Cut-and-paste Fehler.
Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.