Pointer Array auf Strings in Funktion befüllen
-
Hallo!
Vielleicht kann mich jemand erlösen und mir einen Tip zu einem scheinbar trivialen Problem geben (Code ist etwas verkürzt und vereinfacht dargestellt):In der main Funktion, wird ein Zeiger-Array deklariert (für eine Liste von Strings), ein Pointer auf dieses Array in die Funktion "Befuellen" übegeben. Nachdem die Funktion erfolgreich durchlaufen ist, wird der Inhalt ausgegeben.
int main(int argc, char* argv[]) { char *pointerArray[20]; int resultsReturned = Befuellen(pointerArray); for (int i=0; i<resultsReturned; i++) { printf(pointerArray[i]); } }
Die Funktion "Befuellen" sieht wie folgt aus (stark vereinfacht):
int Befuellen(char **arr) { int j; for (j=0; j<20; j++) { char *attributeValue; sprintf(attributeValue, "%S\n", quelle->GibMirEinenStringZurueck(j)); arr[j] = attributeValue; return j; }
Nehmen wir an, dass die Methode quelle->GibMirEinenStringZurueck(j) bei j=0 den String "Text 1", bei j=1 den String "Text 2" liefert,
so kommt bei der Ausgabe in der Main-Funktion immer der String "Text 1" heraus.Wo kann der Fehler liegen?
Vielen Dank & Grüße,
Mark
-
1.) Sowas wie quelle->GibMirEinenStringZurueck(j) geht in C nicht. Aber egal.
2.) In Zeile 2.8 schreibst du nach einfach nach attributeValue
Das ist natürlich riskant, weil der Zeiger ohne Initialisierung irgendwo hinzeigt, du ergo irgendeinen Speicherbereich zu überschreiben versuchst.
Besser wäre, statt dem Zeiger einen Puffer zu definieren (oder halt mit malloc Speicher anzufordern).
-
bgdnoy schrieb:
1.) Sowas wie quelle->GibMirEinenStringZurueck(j) geht in C nicht. Aber egal.
Doch, das geht. Wenn gleich es in C++ üblicher ist.
-
Vielen Dank für Eure Anmerkungen und Vorschläge!
Beides hat aber - denke ich - nichts mit dem Problem zu tun.
Warum bloß zeigt jede Zelle des Pointer-Arrays auf den gleichen String, nämlich in unserem Beispiel "Text 1"?
-
Bei der function's aufruff sprintf
bei dem 2 Parammeter (formatstring) muss %s anstelle von %S
-
Doch, das geht. Wenn gleich es in C++ üblicher ist.
Dem werd ich auf den Grund gehen.
EDIT:
Ahhhhh. Das liegt ganz einfach darin, daß die Derefernzierung schon im -> impliziert ist. Alles klar.
-
Das ist ja wie im Heise-Forum!
Mag sich denn niemand der Herausforderung annehmen und etwas über das Array
char *pointerArray[20];
schreiben?
-
Das hab ich oben schon unter 2.) getan.
Dein Problem liegt nicht an dem Pointer-Array, sondern daran, daß du für jeden Pointer auch eigenen Speicherbereich bereitstellen mußt. Das kannst du, wie gesagt, in Zeile 2.7 machen.
-
int Befuellen(char **arr) { int j; for (j=0; j<20; j++) { // die zeichenkette kann nur 20 zeichen fassen // keine anung wie gross sie aus der quelle->GibMirEinenStringZurueck(j) // herauskommen char *attributeValue = (char*)malloc( 20 + sizeof(char)); sprintf(attributeValue, "%s\n", quelle->GibMirEinenStringZurueck(j)); arr[j] = attributeValue; } return j; }
genau bgdnoy
-
Hey! Ihr habt recht, bei jedem Durchlauf wurde der Speicherbereich des vorigen überschrieben.
Wie Ramsis gesehen hat, müsste hier
sprintf(attributeValue, "%S\n", quelle->GibMirEinenStringZurueck(j));
ja eigentlich %s statt %S stehen.
Ändere ich das große 'S' in ein kleines 's' bekomme ich nur kryptische Zeichen, ich nehme an die Pointer-Addressen, angezeigt.
Ich habe nirgends etwas darüber gefunden.
Hat Jemand eine Idee?
-
Ersetze bitte quelle->gibstringzurueck(j) zum Testen durch itoa(j) (oder sowas ähnliches). Dann poste noch einmal den Code, und zwar als lauffähiges Programm, damit wir wissen, was sich in Summe verändert hat.
Ich kann nämlich mit der letzten Information auch nur raten.