PDA

Archiv verlassen und diese Seite im Standarddesign anzeigen : C Programmierung Zeiger


Gast
2012-08-05, 22:19:02
Hallo,

ich habe folgende Fragen zu Zeigern und hoffe Ihr könnt mir helfen:

1. Wo ist der Unterschied zwischen diesen Schreibweisen?


main()
{
char* str="Mein Text";
char *str2="Mein Text";
char str3[]="Mein Text";
}


Ich würde sagen zwischen str & str2 wird im Endeffekt das gleiche erreicht, nur in einer anderen Schreibweise oder? Bei str3 wird ein Array mit 10 Elementen erzeugt. str3 ist dabei ein Zeiger auf str3[0] und dieser Zeiger kann nicht verändert werden.
Wie ist das aber bei str und str2? Wie kann ich mir das vorstellen? Habe ich hier 10 Zeiger, bei denen *(str+0)=M, *str(+1)=e usw. darstellen? Wie sieht das ganze im Speicher aus? Gibt es dabei ein Array wie bei str3? Diese Zeiger sind dann veränderbar? Was wäre hier der Vorteil?

2. Ich habe zwei Funktionen:


char* fkt1(char* str)
{
...
return str;
}

main()
{
char *test; char text="Hallo";
test=fkt1(text);
}


Hierbei würde die Adresse der Variablen text an die fkt1 übergeben werden. Fkt1 macht dann irgendwas und gibt als ergebnis str zurück. Dieses wiederum wird in test gespeichert. Ist es hierbei möglich, dass fkt1 eine andere string variable außer str zurückgibt? Jede andere Variable wäre doch nur lokal verfügbar? Kann man in so einer Situation also entweder nur str oder eine globale Variable zurückgeben?

GloomY
2012-08-06, 01:12:42
Hallo,

ich habe folgende Fragen zu Zeigern und hoffe Ihr könnt mir helfen:

1. Wo ist der Unterschied zwischen diesen Schreibweisen?


main()
{
char* str="Mein Text";
char *str2="Mein Text";
char str3[]="Mein Text";
}Die ersten beiden sind identisch; Wo das Leerzeichen steht ist egal.

Jedoch gibt es einen funktionalen Unterschied bei str3. Bei 3 wird nur das Array angelegt; bei 1&2 wird das Array angelegt, aber zusätzlich dazu noch eine (Zeiger-)Variable, die mit der Addresse des Arrayanfangs (erstes Element) initalisiert wird.


Ich würde sagen zwischen str & str2 wird im Endeffekt das gleiche erreicht, nur in einer anderen Schreibweise oder? Bei str3 wird ein Array mit 10 Elementen erzeugt. str3 ist dabei ein Zeiger auf str3[0] und dieser Zeiger kann nicht verändert werden.Richtig. Der Name eines Arrays ist gleichzeitig auch ein Zeiger auf das erste Element.


Wie ist das aber bei str und str2? Wie kann ich mir das vorstellen? Habe ich hier 10 Zeiger, bei denen *(str+0)=M, *str(+1)=e usw. darstellen?Nein, du hast das Array und zusätzlich dazu noch einen Zeiger auf den Anfang des Arrays.

Die dritte Variante braucht demnach auch mehr Speicher, weil sie eine variable vom Typ char* mehr hat.

Wie sieht das ganze im Speicher aus? Gibt es dabei ein Array wie bei str3? Diese Zeiger sind dann veränderbar? Was wäre hier der Vorteil?Es gibt bei allen drei Varianten ein Array. str1 und str2 sind veränderbar, da du sie nicht mit
char * const str1 = "...";deklariert hast - in dem Fall wären sie nicht veränderbar.


Vor- und Nachteile: str1 braucht eine zusätzliche Indirektion, d.h. Speicherzugriff. Wenn du
*str1 = 'A';schreibst, brauchst du eine Lese-Operation, um den Wert von str1 aus dem Speicher zu lesen, um dann auf diese Addresse (sprich das erste Element des Arrays) zu schreiben.

Wenn du
*str3 = 'A';schreibst, dann enthält der Maschinenbefehl bereits die Addresse von str3 (die zur Link-Zeit festgelegt wurde). Die einzige Speicheroperation ist somit also der Schreibzugriff. Die Addresse des Arrays steckt im Befehl selbst drin (soweit der Befehlssatz das unterstützt).



2. Ich habe zwei Funktionen:


char* fkt1(char* str)
{
...
return str;
}

main()
{
char *test; char text="Hallo";
test=fkt1(text);
}

Hierbei würde die Adresse der Variablen text an die fkt1 übergeben werden. Fkt1 macht dann irgendwas und gibt als ergebnis str zurück. Dieses wiederum wird in test gespeichert. Ist es hierbei möglich, dass fkt1 eine andere string variable außer str zurückgibt?Klar, möglich ist es.

Jede andere Variable wäre doch nur lokal verfügbar? Kann man in so einer Situation also entweder nur str oder eine globale Variable zurückgeben?Du kannst auch einen Speicherbereich zurückgeben, den du dynamisch innerhalb der Funktion angefordert hast (z.B. mit malloc()).



btw: Du kannst auch [ code] und [ /code] (ohne Leerzeichen) verwenden statt und

Marscel
2012-08-06, 01:30:38
Hatte was überlesen.

GloomY
2012-08-06, 01:39:16
Naja, die Strings, auf die str und str2 zeigen, können in einem nicht beschreibbaren Speicherbereich liegen, str3 ist dagegen im Stack.

Wenn ich in Windows auf str/str2 schreiben möchte, wird das Programm fehlerhaft beendet.Hmm, ist das bei Strings immer so? Oder nur unter Windows?

Ist es also egal, ob ich
char *s = "bla";oder
const char *s = "bla";schreibe?

GloomY
2012-08-06, 02:06:59
Antwort (http://stackoverflow.com/questions/2589949/c-string-literals-where-do-they-go) hier.

Okay, string-literale müssen nicht umbedingt read-only sein - das ist plattform-abhängig. Was der C-Standard aber sagt ist, dass wenn man sie beschreibt, erhält man undefiniertes Verhalten. In dem Fall sollte man also lieber ein Array verwenden.

Marscel
2012-08-06, 02:42:19
Hmm, ist das bei Strings immer so? Oder nur unter Windows?

Naja, er hatte ja nach dem Verändern von Zeigern gefragt, nicht nach den Strings - wie ich erst beim 2. Lesen festgestellt habe. Insofern ja, die Zeiger können natürlich bearbeitet werden.