Wer kennt sich mit string.h aus?

OP #680550
Lesenswert?
• ▲
▼
Hallo zusammen,

Ich bin dabei mein MC35T mit dem ATmega16 auszulesen. Ankommende Daten 
zeige ich auf einem LCD- Display an.
Wenn ich dem Befehl zum senden eines Telfonbucheintrags abschicke, 
bekomme ich ein String mit den geforderten Daten. Soweit klappt das 
auch. Jetzt weiß ich, dass sowohl der Name, als auch die Nummer in 
Anführungszeichen <“> stehen. Ich merke mir, während das Array gefüllt 
wird, wo die 4 Anführungszeichen stehen. Wenn die Übertragung fertig 
ist, fülle ich die zwei Strings „name“ und „nummer“. Also habe ich eine 
Funktion geschrieben die sieht so aus:


void get_from_mc35t()
{
  U8 i = 0;
  temp[zaehler] = uart_getchar(); // in temp kommt das aktuelle 
empfangene Zeichen

      // hier wird das vierte Array-Platz gespeichert in dem das erste
      // < " > platziert ist
      if((temp[zaehler] == '"') &&(anf_zeich3 != 0)&&(anf_zeich4 == 0))
        {
          anf_zeich4 = zaehler;
        }

      // hier wird das dritte Array-Platz gespeichert in dem das erste
      // < " > platziert ist
      if((temp[zaehler] == '"') &&(anf_zeich2 != 0)&&(anf_zeich3 == 0))
        {
          anf_zeich3 = zaehler;
        }

      // hier wird das zweite Array-Platz gespeichert in dem das erste
      // < " > platziert ist
      if((temp[zaehler] == '"') &&(anf_zeich1 != 0)&&(anf_zeich2 == 0))
        {
          anf_zeich2 = zaehler;
        }

      // hier wird der erste Array-Platz gespeichert in dem das erste
      // < " > platziert ist
      if((temp[zaehler] == '"') &&(anf_zeich1 == 0))
        {
          anf_zeich1 = zaehler;
        }


      ///// Anfang der Auswertung nach empfangen des OK[CR][LF]
      if((temp[zaehler] == LF) && (temp[zaehler-1]== CR) && 
(temp[zaehler-2]== 'K') && (temp[zaehler-3] == 'O'))
      {
        lcd_clear();



        for(i = 0; i< (anf_zeich2 - anf_zeich1 -1); i++)
          {
            eintrag.nummer[i] = temp[anf_zeich1 +1 +i];
           }
        eintrag.name[i+2] = 0; // Am Ende noch eine Null dran hängen

        // hier wird vom dritten bis zum vierten < " > der Name in das 
Array
        // geschrieben
        for(i = 0; i< (anf_zeich4 - anf_zeich3 -1); i++)
          {
            eintrag.name[i] = temp[anf_zeich3 +1 +i];
           }
        eintrag.nummer[i+2] = 0; // Am Ende noch eine Null dran hängen


        lcd_gotoxy(1,1);
        lcd_text("Name:");
        lcd_gotoxy(1,2);
        lcd_text(eintrag.name);
        lcd_gotoxy(1,3);
        lcd_text("Nummer:");
        lcd_gotoxy(1,4);
        lcd_text(eintrag.nummer);

        i = 0;
        zaehler = 0;
        anf_zeich1 = 0;
        anf_zeich2 = 0;
        anf_zeich3 = 0;
        anf_zeich4 = 0;
      }  ///// Ende der Auswertung nach empfangen des OK[CR][LF]

      else // bezieht sich auf das "if" der Auswertung OK[CR][LF]
      {
        zaehler++;
      }


}// Ende get_from_mc35t()


Ich weiß, der Aufruf:
eintrag.nummer[i+2] = 0;
Sieht komisch aus, aber nur so geht das ganze.
Das ganze funktioniert eigentlich ganz gut. Allerdings nur so lange bis 
ich z.B. einen Namen mit 15 Zeichen gelesen habe, und dann einen mit nur 
10. Dann steht im String noch der Rest vom letzten. (der ganze Rest)

Jetzt ist meine Frage ob es bei den vielen Stingfunktionen nicht eine 
gibt, die mir dabei etwas mehr helfen könnte wie das zählen der 
Anführungszeichen. Ich habe zwar schon im Internet gesucht, allerdings 
gibt es nie Beispiele dazu.

Hat von euch jemand eine Idee????
Oder gibt es eine hilfreiche Internet- Seite??

Danke schon mal für eure Hilfe…
Grüße,
Marcel
Gast #680611
Lesenswert?
• ▲
▼
Hier ein anderer Denkanstoss, ganz ohne sring.h

#define WAITNAME    0
#define READNAME    1
#define WAITNUMMER  2
#define READNUMMER  3
#define WAIT_O      4
#define WAIT_K      5
#define WAIT_CR     6
#define WAIT_LF     7

char Name[40];
char Nummer[40];
byte Cnt;
char Char = uart_getchar();
switch (State)
{
case WAITMAME:
    if (Char != '\"')
        break;
    State = READNAME;
    Cnt = 0;
    break;
case READNAME:
    if (Char != '\"')
    {
        Name[Cnt++] = Char;
        break;
    }
    State = WAITNUMMER;
    break;
case WAITNUMMER:
    if (Char != '\"')
        break;
    State = READNAME;
    Cnt = 0;
    break;
case READNUMMER:
    if (Char != '\"')
    {
        Name[Cnt++] = Char;
        break;
    }
    State = WAIT_O;
    break;
case WAIT_O:
    State = Char == 'O' ? WAIT_K : WAIT_NAME;
    break;
case WAIT_K:
    State = Char == 'K' ? WAIT_CR : WAIT_NAME;
    break;
case WAIT_CR:
    State = Char == '\r' ? WAIT_LF : WAIT_NAME;
    break;
case WAIT_LF:
    State = WAIT_NAME;
    if (Char == '\n')
        // Fertig, Datenverarbeitung
    break;
}
OP #680638
Lesenswert?
• ▲
▼
Hallo  Durchblicker,

hmmm, ich bin noch kein all zu gutern Programmierer!!! Da brauche ich 
erst mal ne weile bis ich deinen Code richtig verstehe.

Aber auf jeden Fall mal vielen Dank für deinen Denkanstoss.

Ich gehe mal davon aus das "State" eine globale Variable ist!!



ich könnte für die Anzeige also noch schreiben:

#define WRITE_LCD     8



und dann unten:

case WAIT_LF:
    State = WRITE_LCD;
    if (Char == '\n')
    break;

case WRITE_LCD:
    State = WAIT_NAME;
    if (Char == '\n')
        // Fertig, Datenverarbeitung
        ///// Ausgabe auf dem LCD !!!
    break;



ist das so richtig??

Grüße Marcel
Gast #680885
Lesenswert?
• ▲
▼
Ja genau. Ausserdem habe ich die Nullterminierung vergessen, und bei 
READNUMMER hab ich in Name reingespeichert... :

case READNAME:
    if (Char != '\"')
    {
        Name[Cnt++] = Char;
        break;
    }
    Name[Cnt] = 0;
    State = WAITNUMMER;
    break;

case READNUMMER:
    if (Char != '\"')
    {
        Nummer[Cnt++] = Char;
        break;
    }
    Nummer[Cnt] = 0;
    State = WAIT_O;
    break;

Was bei Deinem Code schiefläuft, weiss ich allerdings auch nicht...
OP #681773
Lesenswert?
• ▲
▼
@ Durchblicker,

so jetzt geht's endlich mit deinem "Denkanstoss" :o))

Es hat die ganze Zeit bei mir nicht funktioniert da ich einen Denfehler 
drin hatte.

1. Mann epfängt nicht automatisch nach dem letzten  "  das  OK\n\r . Das 
heißt die Funktion für  \n  und  \r  mußte hier so geschrieben werden 
wie bei dem ".

2. Man muss gleich beim  \r  auf das LCD geschrieben werden. Man kann 
nicht in  \r  schreiben: Status = WRITE_LCD da  \r  ja das letzte 
empfangene Zeichen ist und so die Funktion nicht mehr aufgerufe wird.

Wie gesagt, jetzt klappt das ganze aber hervorragend.

Viele Dank für deinen klasse Tip!!!!

Schönen Sonntag Abend noch und Grüße,

Marcel

Antwort schreiben

Bitte melde dich an, um einen Beitrag zu schreiben.

oder

Mit Google-Account einloggen

Die Registrierung ist kostenlos und dauert nur eine Minute.

Jetzt registrieren