Forum: Compiler & IDEs #define's zusammenfassen


von Alex B. (gebo)


Lesenswert?

Nabend zusammen,

ich arbeite gerade an einem Projekt, bei dem eine Tür über RFID geöffnet 
werden soll. Das eigentlich Programm läuft auch super, allerdings habe 
ich ein Problem bei einer Abfrage.

Ich lege die zugelassenen IDs via #define fest, etwa so:
1
#define TRANSPONDER1 "010C81231234"
2
#define TRANSPONDER2 "35017C123455"
3
#define TRANSPONDER3 "850123449876"
4
#define TRANSPONDER4 "456DS71H2345"
5
#define TRANSPONDER5 "120035094321"
6
#define TRANSPONDER6 "16003C3A1234"
7
#define TRANSPONDER7 "150071369AC8"

Mein jetziges Programm holt sich nun eine cardID via RFID und speichert 
sie als string, um sie dann wie filgt zu vergleichen:
1
if(strcmp (cardID,TRANSPONDER1) == 0 ) 
2
{
3
    OK();
4
} 
5
else if(strcmp (cardID,TRANSPONDER2) == 0 ) 
6
{
7
    OK();
8
} 
9
.
10
.
11
.
12
else 
13
{
14
   FAIL();
15
}

Das wird bei zunehmender Zahl an IDs (obwohl es kaum mehr als 10 werden, 
aber man weiß ja nie) etwas unübersichtlich und scheint mir doch 
irgendwie etwas leienhaft (was ich ja auch bin) programmiert zu sein. 
Gibt es z.B. die Möglichkeit ein TRANSPONDER[]-array anzulegen, dass ich 
bei meiner Abfrage durchlaufe?

Danke für die Hilfe
LG

Alex

von Klaus (Gast)


Lesenswert?

Durchaus. Das Problem ist sogar so häufig, das es in den gängigen 
Büchern über Programmiersprachen in besonderen Kapiteln abgehandelt 
wird.

von Tom (Gast)


Lesenswert?


von Karl H. (kbuchegg)


Lesenswert?

Alex B. schrieb:

 Gibt es z.B. die Möglichkeit ein TRANSPONDER[]-array anzulegen, dass 
ich
> bei meiner Abfrage durchlaufe?

Sicher.
1
const char* Transponder[] = { "010C81231234",
2
                              "35017C123455",
3
                              "850123449876",
4
                              "456DS71H2345",
5
                              "120035094321",
6
                              "16003C3A1234",
7
                              "150071369AC8",
8
                            };
9
10
#define ARRAY_SIZE(x) ((sizeof(x)/sizeof(*x))
11
12
13
...
14
15
    for( i = 0; i < ARRAY_SIZE( Transponder ) ) {
16
      if( strcmp( cardID, Transponder[i] ) == 0 )
17
        OK();
18
    }
19
...

Ich kann nur meine Standardaufforderung anbringen, sich doch mal ein 
C-Buch zu kaufen und da zumindest die erste Hälfte durchzuarbeiten. 
Derartige Standard-Aufgaben sollten auch Nicht-Profis vor keinerlei 
Probleme stellen. Wie will man denn einigermassen vernünftig 
programmieren, wenn man 80% seiner sprachlichen Möglichkeiten gar nicht 
kennt?

von Klaus (Gast)


Lesenswert?

for( i = 0; i < ARRAY_SIZE( Transponder ) )


Jetzt musste ich doch gerade mal fett grinsen. :-)))))))))
Aber natürlich bei Dir nur ein Tippfehler.

von Andreas S. (Firma: Schweigstill IT) (schweigstill) Benutzerseite


Lesenswert?

Karl Heinz schrieb:
> Wie will man denn einigermassen vernünftig programmieren, wenn
> man 80% seiner sprachlichen Möglichkeiten gar nicht kennt?

Man lässt programmieren. Du hast doch selbst demonstriert, dass dieser 
Ansatz funktioniert.

von Karl H. (kbuchegg)


Lesenswert?

Klaus schrieb:
> for( i = 0; i < ARRAY_SIZE( Transponder ) )
>
>
> Jetzt musste ich doch gerade mal fett grinsen. :-)))))))))

:-)
Jetzt hab ich auch 2 mal schauen müssen, bis es mir wie Schuppen von den 
Haaren gefallen ist. Da fehlt ja der Increment.
Na, ja. Den wird er ja wohl noch alleine hinkriegen.

> Aber natürlich bei Dir nur ein Tippfehler.

Den der Compiler gefunden hätte. Wenn schon Fehler machen, dann so, dass 
der Compiler sie finden kann.

von Andreas S. (Firma: Schweigstill IT) (schweigstill) Benutzerseite


Lesenswert?

Klaus schrieb:
> Aber natürlich bei Dir nur ein Tippfehler.

Oder der dezente Hinweis an den Threadersteller, dass er den Fehler 
selbst finden soll. :-)

von Klaus (Gast)


Lesenswert?

Karl Heinz schrieb:
> Klaus schrieb:
>> Aber natürlich bei Dir nur ein Tippfehler.
>
> Den der Compiler gefunden hätte. Wenn schon Fehler machen, dann so, dass
> der Compiler sie finden kann.

Ja, ja. Das sage ich auch immer. :-)

Wobei die hier übliche Übersetzung des Compilerfehlers sein wird: Es 
geht nicht.

von Alex B. (gebo)


Lesenswert?

Danke für die schnelle Hilfe.
Den o.g. Thread werd ich mir mal durchlesen und auch diesen Ansatz hier 
im Thread testen.

Den Hinweis mit den Büchern werd ich bei zeiten mal beherzigen. Und ich 
glaube, dass ich weit mehr als 80% meiner Möglichkeiten NICHT kenne. 
Also danke für die Blumen ;)

Euch allen einen schönen Abend.

von Amateur (Gast)


Lesenswert?

Vergiss die Einzeldefinitionen!

#define AnzahlAnDefinitionen 7 // Kann nach Bedarf vergrößert werden

int Zaehler;

char NeueDefinitionen [ AnzahlAnDefinitionen  ] [ 13 ] = (
  "010C81231234",
  "35017C123455",
  "850123449876",
  "456DS71H2345",
  "120035094321",
  "16003C3A1234",
  "150071369AC8" );

for ( Zaehler = 0; Zaehler < AnzahlAnDefinitionen  ; ++Zaehler ) {
if ( strcmp ( cardID, NeueDefinitionen [ Zaehler] ) == 0 )
  {
    OK();
    break;
  }
}
// Hier (Zaehler == AnzahlAnDefinitionen) (nix gut) abfragen

Wenn Du unbedingt auf #define stehst, kannst Du auch die Definitionen in 
das Array stellen.

von Klaus (Gast)


Lesenswert?

Alex B. schrieb:
> Danke für die schnelle Hilfe.
> Den o.g. Thread werd ich mir mal durchlesen und auch diesen Ansatz hier
> im Thread testen.
>
> Den Hinweis mit den Büchern werd ich bei zeiten mal beherzigen. Und ich
> glaube, dass ich weit mehr als 80% meiner Möglichkeiten NICHT kenne.
> Also danke für die Blumen ;)
>
> Euch allen einen schönen Abend.

Das lobe ich mir. Bedankst Dich und gelobst Besserung. Viel Erfolg und 
bis zum nächsten Mal.

von Dirk B. (dirkb2)


Lesenswert?

Oder
1
const char* Transponder[] = { "010C81231234",
2
                              "35017C123455",
3
                              "850123449876",
4
                              "456DS71H2345",
5
                              "120035094321",
6
                              "16003C3A1234",
7
                              "150071369AC8",
8
                              NULL             /* Als Endekennung */
9
                            };
10
11
...
12
13
    for( i = 0; Transponder[i] /* != NULL */ ;i++ ) {

von Alex B. (gebo)


Lesenswert?

Dirk B. schrieb:
> Oder
>
1
> const char* Transponder[] = { "010C81231234",
2
>                               "35017C123455",
3
>                               "850123449876",
4
>                               "456DS71H2345",
5
>                               "120035094321",
6
>                               "16003C3A1234",
7
>                               "150071369AC8",
8
>                               NULL             /* Als Endekennung */
9
>                             };
10
> 
11
> ...
12
> 
13
>     for( i = 0; Transponder[i] /* != NULL */ ;i++ ) {
14
>

Danke.
Das mit dem NULL klappt super. Hab die o.g. Vorschläge dahingehend 
geändert.
Spart mir ein #define.

Code sieht wie folgt aus:
1
for( int i = 0; i < 12; i++ ) 
2
{
3
  cardID[ i ] = uart_getc();
4
}
5
cardID[ 12 ] = 0;
6
        
7
//lcd_clrhome();
8
//lcd_setpos(0,0);
9
//lcd_string("ID: ");
10
//lcd_string(cardID);
11
      
12
for( int k = 0; Transponder[k]; k++ )
13
{
14
  if( strcmp( cardID, Transponder[k] ) == 0 )
15
  {
16
    OK();
17
    break;
18
  }
19
}

Das klappt super. Ich habe jetzt mehrere Möglichkeiten probiert den 
'negativen' Fall (keine Karte passt) einzubauen. Resultat ist entweder:

1) er springt immer in FAIL() z.B. wenn ich else FAIL() mit in die 
for-Schleife nehme. Das kann ich mir ja noch erklären. Er muss ja alle 
gespeicherten IDs checken.
2) das NULL abfragen funktioniert anscheinend auch nicht, so wie ich das 
verstehe is das ja keine 0 ?????

Würde ggf. ein Vergleich von k und sizeof meines Transponder-Arrays was 
bringen? Nur als Idee? Wie ich das umsetzen könnte weiß ich auch noch 
nicht.

von Little B. (lil-b)


Lesenswert?

Ich mach das für gewöhnlich so:
1
int k;
2
3
// durchsuche liste, breche ab, wenn gefunden
4
for( k = 0; Transponder[k]; k++ )
5
{
6
  if( strcmp( cardID, Transponder[k] ) == 0 )
7
  {
8
    OK();
9
    break;
10
  }
11
}
12
// komplette liste durchsucht?
13
if (Transponder[k] == NULL) {
14
  FAIL();
15
}

von Alex B. (gebo)


Lesenswert?

Little Basdart schrieb:
> // komplette liste durchsucht?
> if (Transponder[k] == NULL) {
>   FAIL();
> }

Das macht er bei mir nicht. Er kompiliert das zwar, aber wenn ichs mit 
ner falschen ID teste, springt er einfach an den Start, überspringt die 
Abfrage also bzw. sieht sie als FALSCH an

von Dirk B. (dirkb2)


Lesenswert?

Alex B. schrieb:
> das NULL abfragen funktioniert anscheinend auch nicht, so wie ich das
> verstehe is das ja keine 0 ?????
Jain.

Transponder[k] ist ein char* (Zeiger auf char).
Und bei Zeigern nimmt man NULL. Das ist lesbarer.

NULL ist in stdlib.h definiert als 0 oder 0L oder (void*)0
( http://www.cplusplus.com/reference/cstdlib/NULL/ )

Es ist also schon eine 0 (sonst würde die Bedingung der for-Schleife 
nicht funktionieren), wird aber anders gelesen.
NULL bedeutet mehr "ungültiger Zeiger"

von Max H. (hartl192)


Lesenswert?

Versuch mal das "int k = 0;" vor die Schleife zu setzten.

von Alex B. (gebo)


Lesenswert?

Max H. schrieb:
> Versuch mal das "int k = 0;" vor die Schleife zu setzten.


macht erstmal keine Unterschied. Für die Version von LitteBasdart musste 
ich da aber eh machen.

von Alex B. (gebo)


Lesenswert?

Dirk B. schrieb:
> Alex B. schrieb:
>> das NULL abfragen funktioniert anscheinend auch nicht, so wie ich das
>> verstehe is das ja keine 0 ?????
> Jain.
>
> Transponder[k] ist ein char* (Zeiger auf char).
> Und bei Zeigern nimmt man NULL. Das ist lesbarer.
>
> NULL ist in stdlib.h definiert als 0 oder 0L oder (void*)0
> ( http://www.cplusplus.com/reference/cstdlib/NULL/ )
>
> Es ist also schon eine 0 (sonst würde die Bedingung der for-Schleife
> nicht funktionieren), wird aber anders gelesen.
> NULL bedeutet mehr "ungültiger Zeiger"

Danke :) Jetzt weiß ich zumindest was NULL genau tut.
Gibts es ne Möglichkeit NULL abzufragen?

LG
Alex

von Dirk B. (dirkb2)


Lesenswert?

Alex B. schrieb:
> Danke :) Jetzt weiß ich zumindest was NULL genau tut.
> Gibts es ne Möglichkeit NULL abzufragen?

Hat doch   Little Basdart schon gezeigt (darum habe ich es nicht nochmal 
geschrieben)

Alex B. schrieb:
> Das macht er bei mir nicht. Er kompiliert das zwar, aber wenn ichs mit
> ner falschen ID teste, springt er einfach an den Start, überspringt die
> Abfrage also bzw. sieht sie als FALSCH an
Sie soll doch falsch sein ???

Zeig mal die ganze Abfrage bzw den Code(geht auch als Anhang).

von Jörg W. (dl8dtl) (Moderator) Benutzerseite


Lesenswert?

Karl Heinz schrieb:
> Wenn schon Fehler machen, dann so, dass der Compiler sie finden kann.

Den musste ich gleich mal in die „Quips“ unseres Bugzillas einkippen. 
;-)

von Alex B. (gebo)


Lesenswert?

Dirk B. schrieb:
> Alex B. schrieb:
>> Danke :) Jetzt weiß ich zumindest was NULL genau tut.
>> Gibts es ne Möglichkeit NULL abzufragen?
>
> Hat doch   Little Basdart schon gezeigt (darum habe ich es nicht nochmal
> geschrieben)
>
> Alex B. schrieb:
>> Das macht er bei mir nicht. Er kompiliert das zwar, aber wenn ichs mit
>> ner falschen ID teste, springt er einfach an den Start, überspringt die
>> Abfrage also bzw. sieht sie als FALSCH an
> Sie soll doch falsch sein ???
>
> Zeig mal die ganze Abfrage bzw den Code(geht auch als Anhang).

Ok, hab nen ganz billigen Fehler in LittleBastdarts Code drin gehabt.
Klappt wunderbar. DANKE
Naja, Übung macht den Meister...

> Wenn schon Fehler machen, dann so, dass der Compiler sie finden kann.
Das muss ich mir merken :D:D:D:D

von Dirk B. (dirkb2)


Lesenswert?

Alex B. schrieb:
> Naja, Übung macht den Meister...

... und Fehler machen.

von rfidler (Gast)


Lesenswert?

bist du dir mit deinem Transponder4 eigentlich sicher?
So eine UID habe ich noch nie gesehen.

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
Noch kein Account? Hier anmelden.