C++ Ende des Strings fehlt aufgrund von strcpy

EueRolando

Cadet 2nd Year
Registriert
Aug. 2014
Beiträge
29
Hallöchen,

ich benötige mal einen Vorschlag, wie ich mein Problem umgehen bzw. lösen kann.
Folgendes Problem:
Ein Array mit 5 Elementen vom Typ sBuchEintrag existiert.
Der struct sBuchEintrag hat 3 char-Array und 2 int Member.
Das Array wird wie folgt initialisiert:

Code:
void ArrayInitialisieren(sBuchEintrag *array, int anzahleinträge){

	for (int i = 0; i < anzahleinträge; i++) {
		array[i].next=NULL;
		strcpy(array[i].author,"Kein Author");
		strcpy(array[i].titel,"kein Titel");
		strcpy(array[i].isbn,"kein ISBN");
		array[i].bibliotheksnr=i+1;
		array[i].kaufdatum=0;
		}
	}

Wenn ich irgendwo im Programm mit cout einen string-Member ausgeben will fehlt die NULL und der Komplette char-Speicher eines Elements wird ausgegeben.

Wenn man mit "echten" strings arbeitet ist diese Art der Manipulation: strcpy(array.author,"Kein Author"); nicht nötig. Leider ist mir nicht bekannt wie dies im Zusammenhang mit dem Array gehen soll. Mal nebenher: Das Mit dem Array muss so bleiben.
Später werde ich die char Member im Array individuell manipulieren. Auch da wird dann das Problem mit der NULL auftauchen.

Kann mir jemand sagen wie ich das lösen kann?

Grüße
EueRolando
 
Wenn die ne NULL fehlt, dann häng sie doch einfach dran.

strcpy(array.author,"Kein Author\0");
strcpy(array.titel,"kein Titel\0");
strcpy(array.isbn,"kein ISBN\0");

Ich hab C++ jetzt nicht so im Kopf, aber woher weiß strcpy eigentlich wie viele Zeichen es kopieren soll?
Gibts da einen Parameter wo man das einträgt oder verlässt sich der Befehl nur auf das Vorhandensein von \0 ?
 
Eine Zeichenkette in Form von "Text" ist in C++ doch automatisch mit \0 terminiert, oder? Daher weiß strcpy auch wie viel er kopieren muss, eben bis zum Abschlusszeichen.

Aber was mir da irgendwie fehlt: wo wird der Speicher im Struct für die Strings initialisiert? Oder kopierst du per strcpy wild an irgendwelchen uninitialisierten Speicher?
 
Wieviel Byte hast du denn für die Arrays reserviert ( titel[???] )?
Sind die ordentlich initialisiert ( memset )?

Das strcpy kopiert immer das erste '\0' mit und endet dann.
http://www.cplusplus.com/reference/cstring/strcpy/

Wenn in deinem Beispiel für author nur 3 Byte reserviert sind du aber 12 Byte rein schreiben willst
wird der Rest in den dahinter liegenden Speicherbereich geschoben egal was da ist.
In deinem Beispiel ist es vermutlich "nur" die Variable titel und knallt deswegen wohl nicht.

Das cout wiederum liest solange im Speicher bis es auf ein '\0' trifft.
http://www.cplusplus.com/reference/iostream/cout/?kw=cout

Du kannst wie du gesagt hast auch einfach mit std::string arbeiten, dann hat das einen
copy-konstruktor und der Operator "= " ist überladen. Dann kannst du einfach
author = "Kein Author" schreiben.
 
Zuletzt bearbeitet: (Rs, Sb)
Das, was Du da machst, ist C. Ohne ++.

Du solltest wirklich darüber nachdenken, ob Du deine Struktur nicht doch anpassen kannst. Derzeit sieht die (vermutlich) irgendwie so aus:
Code:
struct {
	char* author,
	char* titel,
	char* isbn,
	int bibliotheksnr,
	int kaufdatum
}

Besser wäre es so:
Code:
struct {
	std::string author,
	std::string titel,
	std::string isbn,
	int bibliotheksnr,
	int kaufdatum
}

Dann kannst Du das auch einfach zuweisen:
Code:
array[i].author = "Max Mustermann";

Hintergrund: C++ kann assignment operators. Bei std::string gibt es den auch für const char*.

[edit:]
Vielleicht noch zum eigentlichen Problem mit deiner C-Struktur, auch wenn es im groben schon genannt wurde:
Der Speicherbereich für die char*-Strings deiner struct wird vermutlich nicht initialisiert, das kannst Du auf zwei Arten "umgehen".

Möglichkeit 1: Feste Allokation innerhalb deiner Struktur:
Code:
struct {
	char author[32],
	char titel[128],
...
}
Das ist nichtmal so selten und wird desöfteren gemacht.

Möglichkeit 2: Speicher bei Belegung allozieren:
Code:
const char* source_str = "Max Mustermann";
if(!(array[i].author = calloc(strlen(source_str) + 1, sizeof(char)))) {
	// fehler beim speicher holen
}
strcopy(array[i].author, target_str);
Ich denke, Du siehst schon, dass das eher umständlich ist.
 
Zuletzt bearbeitet:
Also mein struct sieht so aus:

Code:
struct sBuchEintrag{
	sBuchEintrag *next;
	char author[20];
	char titel[20];
	char isbn[20];
	unsigned short bibliotheksnr;
	unsigned int kaufdatum;
};

Aber ich werde es in std::string ändern. Dachte das gibt es nur in Delphi o.ä..

Vielen Dank!
EueRolando:)
 
Kannst du mal
a) die Deklaration von sBuchEintrag und
b) die Initialisierung des Arrays (also den Teil, wo die Variable angelegt bzw. der Speicher reserviert wird)
zeigen?
Ich würde hier auch tendenziell auf nichtinitialisierten Speicher tippen.

\begin rant
Davon abgesehen ist das im Prinzip kein c++ sonder c code und falls euch euer Prof (oder wer auch immer) solche Aufgaben in einem c++ Kurs stellt, bzw. diese Art von Lösung erwartet, dann sollte er besser den Lehrberuf an den Nagel hängen.
\end rant
 
Zurück
Oben