Enums mit Platzhaltern

Hallo,

ich verwende mittlerweile gerne Enums. Oft kommt es hierbei vor, dass ich z.B. 0, 1 und 2 per Enum definieren und im Anschluss ein paar Folgewerte unbenannt lassen möchte. Diese habe ich in dem Beispielcode mit LEER gekennzeichnet, was so ja zunächst einmal nicht funktioniert.

enum {
  OFF, ON,
  500MS, LEER, LEER, LEER, LEER, LEER, LEER, LEER, LEER,
  GLOW1, GLOW2, GLOW3, GLOW4, GLOW5
};

Was kann ich anstatt LEER schreiben, wenn ich an diesen Positionen vorerst keine Bezeichnungen (wie z.B. OFF oder ON) benötige?

Gruß Chris

enum {OFF=0, ON=1, GLOW1=10, GLOW2, GLOW3};

GLOW2 hat dann den Wert 11

Falls es das ist, was du willst.

Nachtrag:
Puristen fordern allerdings, dass dein Code unabhängig vom aktuellen Wert immer funktionieren sollte. Platzhalter oder Zuweisungen sind dann unnötig.
Warum willst du denn, dass zwischen _500MS und GLOW1 eine Lücke ist ?

michael_x: Warum willst du denn, dass zwischen _500MS und GLOW1 eine Lücke ist ?

Hallo,

zunächst einmal vielen Dank!

Ich verwende Enums für folgenden Fall:

Ein Byte ist jeweils einer LED zugeordnet. Über den Wert dieses Bytes definiert sich, wie die entsprechende LED zu blinken hat.

0 = LED aus 1 = LED an 2 = LED geht alle 500ms an/aus 3 = LED geht alle 333ms an/aus usw.. 11 = LED blinkt einmal pro Sekunde kurz auf 12 = LED blinkt zweimal pro Sekunde kurz auf usw..

Die Abfrage welche LED wie leuchten soll geschieht über for-Schleifen. Da ich momentan von den Werten 2 bis 10 lediglich die LEDs die alle 500ms an/aus gehen sollen benötige und die sekündlich kurz blinkenden LEDs in einem zusammenhängenden Wertebereich, den man sich leichter merken und leichter abfragen kann bewegen, würde ich die Blinkvarianten gerne jeweils blockweise arrangieren.

2 - 10 periodisch blinkende LEDs 11 - 20 kurz aufblinkende LEDs 21 - 30 undefiniert.. usw..

Somit bin ich was die Erstellung weiterer Blinkvarianten angeht flexibler.

Ich hoffe, es ist nun etwas klarer, warum ich das gerne so machen würde.

Gruß Chris

Verständlich ist es schon.

Bist auch nicht der einzige, der gerne enum Werte mit <= und >= in Gruppen zusammenfasst oder damit rechnen will.
Das geht auch in C wunderbar, besser als in anderen Sprachen :wink:
Eigentlich solltest du aber nicht wissen müssen/wollen, welchen aktuellen numerischen Wert eine enum Variable hat.

typedef enum { A = 0, B, C, D = 10, E } MODE;

void test_enum()
{
   MODE x = A;
   MODE y = x;
   // y = x + 1; // Das geht nicht
   if (A < y && y < 10) { /* y is B or C */ }
}

Ich halte das Vorhaben für einen Irrweg!

Warum?

Gruß Chris

Eigentlich sollen uns enums von der Behandlung der Zahlen befreien.
Dieses sollte man nicht leichtfertig aufgeben.

einem zusammenhängenden Wertebereich, den man sich leichter merken und leichter abfragen kann

Eine mit bedacht gewählte Reihenfolge kann hilfreich sein.

Aber hier die Werte?
Warum sollte man sich die merken wollen?

Probleme treten doch sofort auf, wenn man dieses möchte:

enum farbe {rot=0,violett=1,green=45,lime=46};

orange hinzufügen:

enum farbe {rot,orange,violett,green,lime};

Verzichtet man auf die Zahlen, geht sogar sowas:

// tue was mit den rötliche Farben
  for( int i = rot; i<=violett;i++) 
  {
    // tuwas
  }

Hier ist dann egal ob orange hinzugefügt wurde.

Und, weil ich gerade dabei bin:

enum {

OFF, ON,
  100MS, 333MS,500MS, LEER, LEER, LEER, LEER, LEER, LEER, LEER, LEER,
  GLOW1, GLOW2, GLOW3, GLOW4, GLOW5
};

100MS, 333MS,500MS, solche Benennungen finde ich nicht schön!
Was passiert, wenn dir 333MS nicht mehr gefällt und du hättest da doch gerne 380MS.

Die 333 befinden sich:

  1. in der enum Aufzählung
  2. als Wert in einer Funktion
  3. im Namen der Funktion
  4. eingestreut im Quelltext des Programms

Selbst, wenn 3 nicht zutrifft ist es immer noch eine Mehrfachverwendung. Und erschwert die Wartung.

Auch wenn mich die Benennung GLOW1, GLOW2, GLOW3, GLOW4, GLOW5 wegen der Durchnummerierung stört, warum machst du es bei den Blinkern nicht genau so?
Blink1,Blink2,Blink3,Blink4,Blink5

Ansonsten habe ich noch nicht so ganz verstanden, was du “wirklich” erreichen möchtest.

Die Abfrage welche LED wie leuchten soll geschieht über for-Schleifen.

Da kann ich mir nix drunter vorstellen…

Hier mal die die Frage betreffenden und noch ungetesteten Codeteile. Ob da nun alles mitkopiert wurde wage ich zu bezweifeln, aber ich denke man kann erkennen, wie es angedacht ist.

Mit “glow” ist ein kurzes Aufblitzen einer LED gemeint.

Gruß Chris

// **************************************************  ledParameter  */

byte ledBlinkState[6];       // Status sämtlicher LEDs

const byte LED1 = 28;   // Initialisierung sämtlicher LEDs
const byte LED2 = 34;
const byte LED3 = 40;
const byte LED4 = 46;
const byte LED5 = A3;
const byte LED6 = A0;

const byte ledPin[] = {
  LED1, LED2, LED3, LED4, LED5, LED6
};

void setup()
{
  for (int i = 0; i <= 5 ; i++)
  {
    pinMode(ledPin[i], OUTPUT);      // Definition sämtlicher Outputs
  }
}

enum
{
  OFF, ON,
  500MS,
  GLOW1 = 11, GLOW2, GLOW3, GLOW4, GLOW5
};

void loop()
{
  ledSet();                // Sämtliche LEDs beschalten
}

void ledSet()  // Beschaltet sämtliche LEDs
{
  // static unsigned long now;  // millis() gehört in loop

  static unsigned long lastBlinkTime;  // Startzeitpunk für blinkende LEDs
  const int second = 1000;             // Durchlaufzeit für blinkende LEDs
  const byte glow = 50;                // Brenndauer für kurz blinkende LEDs
  const byte gap = 100;                // Pausendauer für kurz blinkende LEDs
  static byte glowCount;               // Zählt, wie oft kurz blinkende LEDs bereits blinkten

  for (int i = 0; i <= 6; i++)  // LEDs ein/aus
  {
    if (ledBlinkState[i] == OFF) digitalWrite(ledPin[i], LOW);        // LED ausschalten
    else if (ledBlinkState[i] == ON) digitalWrite(ledPin[i], HIGH);  // LED einschalten
  }
  if (now - lastBlinkTime >= second)  // Alle blinkenden LEDs gemeinsam einschalten
  {
    for (int i = 0; i <= 6; i++)
    {
      if (ledBlinkState[i] > 1)
      {
        digitalWrite(ledPin[i], HIGH);
      }
    }
    glowCount = 1;
    lastBlinkTime = now;
  }
  if (now - lastBlinkTime >= second / 2)  // LED mit Status 2 nach 500ms ausschalten
  {
    for (int i = 0; i <= 6; i++)
    {
      if (ledBlinkState[i] == 500MS)
      {
        digitalWrite(ledPin[i], LOW);
      }
    }
    if (now - lastBlinkTime >= ((glow + gap) * glowCount) - gap)  // Glow ausschalten
    {
      for (int i = 0; i <= 6; i++)
      {
        if (ledBlinkState[i] > 10 && ledBlinkState[i] - 10 >= glowCount)
        {
          digitalWrite(ledPin[i], LOW);
        }
      }
    }
    if (now - lastBlinkTime >= (glow + gap) * glowCount)  // Glow einschalten
    {
      for (int i = 0; i <= 6; i++)
      {
        if (ledBlinkState[i] > 10 && ledBlinkState[i] - 10 > glowCount)
        {
          digitalWrite(ledPin[i], HIGH);
        }
      }
      glowCount++;
    }
  }
}

Deine for Schleifen haben einmal die Grenze <= 5 , in ledSet aber <= 6 ( :o )
Guter Stil wäre, dafür ein #define oder const byte zu verwenden.

const byte LEDCOUNT=6;

enum BLINKSTATE ledBlinkState[LEDCOUNT];

const byte ledPin[LEDCOUNT] = {
 28,  34,  40,  46,  A3, A0 };   // meine LED Pins

...
for (byte i = 0; i < LEDCOUNT; i++)
{
        if (ledBlinkState[i] == OFF) digitalWrite(ledPin[i], LOW);        // LED ausschalten
}

Ansonsten würde ich sooft wie möglich (immer) enum Namen verwenden,
und in der enum Definition vermerken, dass die Reihenfolge wichtig ist.

Kannst auch Pseudo-Einträge definieren:

 enum BLINKSTATE {OFF=0, ON=1, FIRST_BLINK, BLINK1000, BLINK500, FLASH1, FLASH2, ..., LAST_ENTRY};

if (ledState[i] > FIRST_BLINK) { /* diverse Blink-Modi */ }

Dass da einmal <=5 und einmal <=6 steht ist gewollt.
Danke für den Hinweis mit den Pseudo-Einträgen. :wink:

Gruß Chris

Chris72622:
Dass da einmal <=5 und einmal <=6 steht ist gewollt.

Aha!
6 LED werden behandelt, aber nur 5 initialisiert.
Da steht " // Definition sämtlicher Outputs"
Das ist nicht sonderlich logisch.

Auch ist mir die Funktion viel zu überladen…

6 LED werden behandelt, aber nur 5 initialisiert.

Nein: es gibt 6 LEDS, die werden alle ( 0 .. 5 ) initialisiert, ausserdem wird auf eine 7. LED zugegriffen, um etwas Abenteuer reinzubringen.

bei ledPin[6] ist unklar, was da geliefert wird.

Jau!
Das stimmt.

Bzgl. den differierenden Werten in den for-Schleifen hattet Ihr recht. :-*

Der Sketch funktioniert nun astrein.

Danke für den Input.

Gruß Chris