mikrocontroller.net

Forum: Compiler & IDEs String Array "indexieren" wie geht das?


Autor: Spannungsteiler (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo Kommunity!

Ich bin dabei C (die Arduino-C) zu lernen, und mit meiner neuen Aufgabe
komme ich nicht weiter. Natürlich habe ich Google schon bemüht, eine 
Lösung zu finden, komme aber einfach nicht weiter.

Ich möchte mit Arduino-UNO über serielle Schnittstelle aus einem
Gerät verschiedene Statuswerte auslesen und danach diesem Gerät
Steuerbefehle schicken. Die Kommunikation funktioniert gut, wenn ich
die Werte und Befehle einzeln lese und schreibe.
Das Ganze schildere ich euch, um zu zeigen was ich in der Praxis 
vorhabe.

Nun zu meiner eigentlicher Frage;
Wie schreibe ich im Arduino-C einen Array, das aus zB. 5 Strings besteht
und durch Indexierung benannt wird ?

Mit Zahlen funktioniert es so:
int i;
int Wertspeicher[5] = { 1, 3, 5, 7, 9 };
int Merker = 0;
void setup() {
  Serial.begin(9600);
  Serial.println("Programm startet...");
  delay(1000);
}
void loop() {
if(Merker==0) {                    // Bildschirmausgabe nur einmal
  for(i=0; i<6; i++) {
    Serial.print("Wert Index: ");
    Serial.print(i);
    Serial.print(" Wertspeicher: ");
    Serial.println(Wertspeicher[i]);
  }
 }
 Merker=1;
}

Ich möchte das Gleiche wie oben, nur diesmal statt Zahlen Worte
nehmen (wie im Beispiel unten;)
int i;
String Worte[5][10] = {"Uhr","Bot","Traktor","Haus","Zange" };
int Merker = 0;
void setup() {
  Serial.begin(9600);
  Serial.println("Programm startet...");
  delay(1000);
}
void loop() {
if(Merker==0) {         // Bildschirmausgabe nur einmal
    for(i=0; i<6; i++) {
    Serial.print("Wert Index: ");
    Serial.print(i);
    Serial.print(" Wertspeicher: ");
    Serial.println(Worte[i]);  <---- wie ist es RICHTIG??????
  }
 }
 Merker=1;
} 
Ich habe mein Problem in 2 kleine Beispiele gehüllt, um euch
das Ganze einfach zu schildern!
Danke für die Hilfe!

Autor: Peter II (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Spannungsteiler schrieb:
> String Worte[5][10] = {"Uhr","Bot","Traktor","Haus","Zange" };

ich kenne jetzt Arduino nicht, aber du willst bestimmt nicht 50 Strings 
haben.
String Worte[5] = {"Uhr","Bot","Traktor","Haus","Zange" };

das ganze ist ja mehr C++, bei C müsste man

char* Worte[5] = {"Uhr","Bot","Traktor","Haus","Zange" };

oder
char Worte[5][10] = {"Uhr","Bot","Traktor","Haus","Zange" };

schreiben.

Autor: Jan L. (ranzcopter)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
const char *Worte[] = {"Uhr","Bot","Traktor","Haus","Zange" };

Autor: Maro (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo,

in deine for-Schleife die dein Array durchgeht muss noch eine 
for-Schleife eingebaut werden, welche die einzelnen chars durchgeht.

for(int i = 0; i < 6; i++ ){
 for(int j = 0; j < strlen(Worte[i]); j++ ){
   Serial.print(Worte[i][j]);
 }
}

So wird in der inneren Schleife jeder Index in der zweiten Dimension des 
Arrays durchgegangen (Buchstabe für Buchstabe). Danach wird in der 
äußeren Schleife jeder Index der ersten Dimension des Arrays 
durchgegangen (Wort für Wort).


srtlen musst du durch eine Funktion ersetzen, die dir die Länge eines 
Strings gibt. Bin mir nicht sicher ob strlen in der Arduino IDE geht.

Autor: Peter II (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Maro schrieb:
> in deine for-Schleife die dein Array durchgeht muss noch eine
> for-Schleife eingebaut werden, welche die einzelnen chars durchgeht.

nein muss nicht,

Serial.print

nimmt ja String entgehen, damit muss man nicht alle Zeichen von Hand 
übergeben.

Autor: Maro (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Na umso besser ^^

Autor: Spannungsteiler (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Vielen Dank für euere Hilfsbereitschaft!!!!

Peter II schrieb:
> ich kenne jetzt Arduino nicht, aber du willst bestimmt nicht 50 Strings
> haben.

:-) nein, aber 45 Strings, wo der Kürzeste aus 5 char besteht und
der Längste aus 9 char. Deshalb möchte ich nicht so viele verschiedene 
Strings mit unterschiedlichen Namen benennen, sondern "Indexieren".

Bei: String Worte[5][10] =....
wollte ich 5 Strings nehmen, wo für jeden 10char reserviert werden.

Jan L. schrieb:
> const char *Worte[] = {"Uhr","Bot","Traktor","Haus","Zange" };

bringt mir die Fehlermeldung;
>> expected unqualified-id before `char´ <<

Autor: Spannungsteiler (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Peter II schrieb:
> nimmt ja String entgehen, damit muss man nicht alle Zeichen von Hand
> übergeben.

Ja das stimmt, aber wie mache ich es wenn ich String[i]
(42xMal nacheinander)am Bildschirm ausgeben möchte?

Deshalb wollte ich ein [i] INDEX verwenden......
(siehe ursprüngliche Frage).

Autor: Spannungsteiler (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Uppssss, so funktioniert es jetzt;
int i;
String Worte[5] = {"Uhr","Bot","Traktor","Haus","Zange" };
int Merker = 0;
void setup() {
  Serial.begin(9600);
  Serial.println("Programm startet...");
  delay(1000);
}
void loop() {
if(Merker==0) {         // Bildschirmausgabe nur einmal
    for(i=0; i<6; i++) {
    Serial.print(" Index: ");
    Serial.print(i);
    Serial.print(" Wort: ");
    Serial.println(Worte[i]);  
  }
 }
 Merker=1;
} 


Dabei verstehe ich nicht ganz, warum ich die Platzhalter [10] für
die Stringlänge nicht angeben muss???
also nicht so;
String Worte[5][10] = {"Uhr","Bot","Traktor","Haus","Zange" };
sonndern so:
String Worte[5] = {"Uhr","Bot","Traktor","Haus","Zange" };

Autor: Erwin D. (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Spannungsteiler schrieb:
> Dabei verstehe ich nicht ganz, warum ich die Platzhalter [10] für
> die Stringlänge nicht angeben muss???
> also nicht so;
> String Worte[5][10] = {"Uhr","Bot","Traktor","Haus","Zange" };
> sonndern so:
> String Worte[5] = {"Uhr","Bot","Traktor","Haus","Zange" };

Weil du sonst 5 mal 10 Strings reservierst.
Wenn du es so schreibst:
char worte[5][10] = {"Uhr","Bot","Traktor","Haus","Zange" };
dann reservierst du 5 mal 10 Chars. Hier mußt du aber eben jedes Zeichen 
einzeln ausgeben (mit der angesprochenen Extra-Schleife).
Oder du schreibst
char worte[5][10] = {"Uhr\0","Bot\0","Traktor\0","Haus\0","Zange\0" };.....
dann wird auch das String-Ende erkannt.
Im Endeffekt ist es aber am übersichtlichsten und am einfachsten, wenn 
du die string-Schreibweise nimmst.
String Worte[5] = {"Uhr","Bot","Traktor","Haus","Zange" };

Autor: Spannungsteiler (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Maro schrieb:
> Bin mir nicht sicher ob strlen in der Arduino IDE geht

die funktionierende Zeile lautet;

     Serial.println(Worte[i]);

und so komme ich auf Stringlänge:

    Serial.println(Worte[i].length());

Super, DANKE für euere Unterstützung!

Es sieht so aus,dass Arduino Compiler die Stringlänge (n) selber im 
Speicher reserviert, deshalb muss ich nicht so deklarieren;

String Worte[i][n]="...........

Ich sehe es mitunter, dass die Anzahl (i) vom Strings auch nicht angeben 
muss!
es reicht einfach  String Worte[]=".......
zu schreiben.

Erwin D. schrieb:
> Im Endeffekt ist es aber am übersichtlichsten und am einfachsten, wenn
> du die string-Schreibweise nimmst.
String Worte[5] = > {"Uhr","Bot","Traktor","Haus","Zange" };

DANKE!!!!

Autor: Jan L. (ranzcopter)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Spannungsteiler schrieb:
> Jan L. schrieb:
>> const char *Worte[] = {"Uhr","Bot","Traktor","Haus","Zange" };
>
> bringt mir die Fehlermeldung;
>>> expected unqualified-id before `char´ <<

bei mir compiliert das einwandfrei:
void loop() {
  // put your main code here, to run repeatedly:
const char *Worte[5] = {"Uhr","Bot","Traktor","Haus","Zange" };
int i;
for(i=0; i<6; i++) {
    Serial.print(" Index: ");
    Serial.print(i);
    Serial.print(" Wort: ");
    Serial.println(Worte[i]);  
  }
}

und bringt die Ausgabe:
Der Sketch verwendet 1.616 Bytes (5%) des Programmspeicherplatzes. Das Maximum sind 32.256 Bytes.
Globale Variablen verwenden 240 Bytes (11%) des dynamischen Speichers, 1.808 Bytes für lokale Variablen verbleiben. Das Maximum sind 2.048 Bytes.

Das gleiche mit "String" tut natürlich auch, benötigt aber fast den 
doppelten Speicher...

Autor: Peter II (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Spannungsteiler schrieb:
> Es sieht so aus,dass Arduino Compiler die Stringlänge (n) selber im
> Speicher reserviert, deshalb muss ich nicht so deklarieren;

das ist ganz normales C++ mit einer String klasse. Es gibt keinen 
"Arduino Compiler" das ist ein normaler gcc

Autor: Spannungsteiler (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Jan L. schrieb:
> bei mir compiliert das einwandfrei:

Hallo Jan! Das ist mir total peinlich! Ich kann es nichtmal
Anfängerfehler nennen, sondern >dumm< ....von mir !

Ich habe den Stern falsch gesetzt, so! ;
const *char Worte[5] = {"Uhr","Bot","Traktor","Haus","Zange" };

dann bekam ich die Fehlermeldung!

Super, dass Du deinen Vorschlag nocheinmal postest!
Ich habe mit pointers noch überhaupt nicht gearbeitet, bin beim
elrernen von Arduino-C++, deshalb ist mir die Schreibweise mit "*"
noch ganz unbekannt.

Das Lernen geht weiter, und ich bin froh, hier im Forum Unterstützung
zu bekommen!!!! DANKE!

Autor: guest (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
  ...
  for(i=0; i<6; i++) {
  ...
Wenn man nur 5 Strings hat sollte man nicht versuchen 6 auszugeben!

Erwin D. schrieb:
> Wenn du es so schreibst:
> char worte[5][10] = {"Uhr","Bot","Traktor","Haus","Zange" };
> dann reservierst du 5 mal 10 Chars. Hier mußt du aber eben jedes Zeichen
> einzeln ausgeben (mit der angesprochenen Extra-Schleife).
> Oder du schreibst
> char worte[5][10] = {"Uhr\0","Bot\0","Traktor\0","Haus\0","Zange\0" };.....
> dann wird auch das String-Ende erkannt.

Das ist Quatsch. Ein Stringliteral enthält schon per Definition die 
abschließende 0, die muß man nicht extra angeben. Notwendig wäre das nur 
wenn man alle Zeichen einzeln angibt:
char worte[5][10] = {
  { 'U', 'h', 'r', '\0' },
  { 'B', 'o', 't', '\0' },
  { 'T', 'r', 'a', 'k', 't', 'o', 'r', '\0' },
  { 'H', 'a', 'u', 's', '\0' },
  { 'Z', 'a', 'n', 'g', 'e', '\0' },
};

Antwort schreiben

Die Angabe einer E-Mail-Adresse ist freiwillig. Wenn Sie automatisch per E-Mail über Antworten auf Ihren Beitrag informiert werden möchten, melden Sie sich bitte an.

Wichtige Regeln - erst lesen, dann posten!

  • Groß- und Kleinschreibung verwenden
  • Längeren Sourcecode nicht im Text einfügen, sondern als Dateianhang

Formatierung (mehr Informationen...)

  • [c]C-Code[/c]
  • [avrasm]AVR-Assembler-Code[/avrasm]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] - Link zu Artikel
  • Verweis auf anderen Beitrag einfügen: Rechtsklick auf Beitragstitel,
    "Adresse kopieren", und in den Text einfügen




Bild automatisch verkleinern, falls nötig
Bitte das JPG-Format nur für Fotos und Scans verwenden!
Zeichnungen und Screenshots im PNG- oder
GIF-Format hochladen. Siehe Bildformate.
Hinweis: der ursprüngliche Beitrag ist mehr als 6 Monate alt.
Bitte hier nur auf die ursprüngliche Frage antworten,
für neue Fragen einen neuen Beitrag erstellen.

Mit dem Abschicken bestätigst du, die Nutzungsbedingungen anzuerkennen.