Algemeines zu char * und char[]

lindin

Erfahrenes Mitglied
Hallo, ich habe eien Farge zu dem Unterschied zwischen char[] und char *!

Ich habe jetzt schon öfter gehört, daß es da keinen unterschied gibt!

Ich denke, der Unterschied ist, daß bei char[] ein fester Speciehr reserviert wird bei der Deklaration!

Aber ich verstehe nicht, wieso es dann nicht bei char * Probleme mit dem Speicher gibt, da, je länger die Variable wird, der Fall wahrscheinlicher wird, daß eine Speicherverletzuing auftritt!

Ich weiß auch, daß es die Möglichkeit mit malloc gibt, um für char * Speicher zu reserviern!
Das muß man aber nicht, man kann char * "einfach so" verwenden!
Aber wieso
 
lindin hat gesagt.:
Hallo, ich habe eien Farge zu dem Unterschied zwischen char[] und char *!

Ich habe jetzt schon öfter gehört, daß es da keinen unterschied gibt!
Das betrifft eher die Übergabe an Funktionen, da ist dann kein Unterschied.

Ich denke, der Unterschied ist, daß bei char[] ein fester Speciehr reserviert wird bei der Deklaration!
Richtig. Bei char* wird direkt gar kein Speicher reserviert (bis auf den für den Zeiger natürlich).

Aber ich verstehe nicht, wieso es dann nicht bei char * Probleme mit dem Speicher gibt, da, je länger die Variable wird, der Fall wahrscheinlicher wird, daß eine Speicherverletzuing auftritt!
Wenn man nicht aufpasst, gerät man bei char* sehr leicht in den Fehlerfall. Ich habe üblicherweise feste Char-Arrays bevorzugt (MAX_PATH oder 260 o.ä.).

Ich weiß auch, daß es die Möglichkeit mit malloc gibt, um für char * Speicher zu reserviern!
Das muß man aber nicht, man kann char * "einfach so" verwenden!
Aber wieso
Das kann nur dann klappen, wenn man einen konstanten Wert benutzt wie:

char* szHallo = "Hallo Welt!"

Solange von dem Pointer nur dieser String gelesen wird, ist das völlig in Ordnung. Der Compiler belegt in diesem Fall den Speicher für den String und setzt den Zeiger auf die Adresse.
Das geht natürlich ganz schnell in die Hose, wenn man auf den Pointer schreibend zugreift. Mit etwas Glück passiert nichts (kein Speicher-Schreibschutz, innerhalb des belegten Speichers geblieben) oder eben auch ein Absturz direkt beim Aufruf.
Oder, am allerschlimmsten, ein Absturz, wo er absolut nicht vermutet wird, weil man eben doch über den Speicherbereich rausgeschrieben hat.

Ach ja, wer in C++ heute statt std::string noch char* oder char[] benutzt, hat entweder sehr gute Gründe (wüsste auf Anhieb keinen) oder seine Probleme einfach verdient.
 
Ahso, std:string ist also besser :)

Ich nutze char, da mir früher nur ansi-c eingetrichtert wurde!

Also fahr ich am besten, wenn ich stat char * immer char[] verwende, alles klar!

Streng genommen sollte man also gar nicht char * verwenden, wenn man das nicht in der Form
char * x="kjsfd" ;

sondern
char * x;
x="kjsfd";

macht!

Hm hm, also ich verstehe einfach nicht, wieso die Benutzung von char * dann in der Form überhaupt möglich ist, müßte denn dann ein Compiler nicht eine Fehlermeldung ausgeben?
 
Ahso, std:string ist also besser :)
Ich nutze char, da mir früher nur ansi-c eingetrichtert wurde!
Mach es wie du willst, kann beides Vorteile haben, kommt auf den Anwendungsfall an.


Streng genommen sollte man also gar nicht char * verwenden, wenn man das nicht in der Form
char * x="kjsfd" ;
sondern
char * x;
x="kjsfd";
macht!
Die beiden Formen machen überhaupt keinen Unterschied. Die meisten (wenn nicht alle) Compiler generieren dafür sogar den gleichen Assembler-Code.
Bei meinem Compiler sieht die Umsetzung folgendermassen aus: Wenn du irgendwo im Quellcode eine Zeichenkette wie "kjsfd" benutzt, wird sie im Datensegment des Prozesses gespeichert. Bei jeder Benutzung wird ein Zeiger auf diese Stelle im Datensegment zurückgegeben, so kann man sogar beliebig oft die gleiche Zeichenkette benutzen, ohne dass dadurch die Exe grösser wird und bei einer Zuweisung eines Zeigers an einen String muss kein Speicher reserviert und nachher wieder freigegeben werden (was auch ziemlich unmöglich wäre). Dafür gibt es unter Umständen Probleme, wenn man in den Buffer schreiben will.

Edit: Mist, falsche Tags benutzt....
 
Du meinst, wenn man folgendes macht:
Code:
char * x ="test";
char * y ="test";

Daß dann beide Variablen auf den gleichen Speicherbereich zugreifen, weil es der gleiche String ist? Oder hab ich das jetzt falsch verstanden?

Aber wenn dann jetzt z.B. x geändert wird, wird dann das geänderte x in einen anderen Speicherbereich geschrieben, und y weist noch auf den selben Speicherbereich wie vorher?
 
char

Also bei der Deklaration wuerde ich auch immer die Vektorversion nehmen, damit mir auch immer klar ist das ich einen string habe und keinen einfachen pointer auf char - aberim weiteren ist die pointerversion sehr schoen kompakt.
 
Also ich habe das bisehre immer so gehandhabt, daß ich die Pointerversion genommen ahbe, wenn ich nicht wußte, wie lang der String wird!
Da gibt es ja auch dann Probleme, wenn man über den allokierten Bereich hinausschreibt!
Ich hatte mir zwar schon gedacht, das char[] besser für die Speicherverwaltung ist!
Hab aber auch gedacht, wenn ich immer char * nehme, dann wird die Datei hinterher so klein wie möglich!
Wenn man nämlich nicht weiß, wie lang der String wird, dann müßte man sehr große Arrays deklarieren, und das macht die exe-DAtei dan natürlich immer größer!

Naja, ich denke, ich bin nun überzeugt davon nur noch arrays zu verwenden :)
 
Du meinst, wenn man folgendes macht:
Code:
char * x ="test";
char * y ="test";
Daß dann beide Variablen auf den gleichen Speicherbereich zugreifen, weil es der gleiche String ist? Oder hab ich das jetzt falsch verstanden?
Genau so mein ich das.

Aber wenn dann jetzt z.B. x geändert wird, wird dann das geänderte x in einen anderen Speicherbereich geschrieben, und y weist noch auf den selben Speicherbereich wie vorher?
Wenn x so geändert wird:
Code:
char * x ="test";
char * y ="test";
x = "was anderes";
dann zeigt x danach natürlich auf einen anderen Speicherbereich, als y.
folgendes:
Code:
char * x ="test";
*x = 'a';
führt bei mir zum Programmabsturz.
Besser wäre:
Code:
char x[] = "test";
//oder:
char* g = new char[256];
strcpy(g,"test");
Beide Fälle stellen sicher, dass kein anderer Zeiger/kein anderes Array den gleichen Speicherberreich nutzt.

edit: Schon wieder Tags verwechselt...
 
@lindin:
Also soweit ich weiß wird durch große Array benutzung wie:
Code:
char ganzganzgroßesArray[512000]; //500 Kbyte
nicht die exe-datei größer. Nur wenn das Programm ausgeführt wird natürlich mehr Platz im Stack beansprucht.
 
Original geschrieben von C Coder
@lindin:
Also soweit ich weiß wird durch große Array benutzung wie:
Code:
char ganzganzgroßesArray[512000]; //500 Kbyte

nicht die exe-datei größer. Nur wenn das Programm ausgeführt wird natürlich mehr Platz im Stack beansprucht.

Yo, denke ich auch. Platz für Variablen wird schließlich selten in die EXE reincompiliert, AFAIK...
 

Neue Beiträge

Zurück