2017-03-04 2 views
0

Ich bin ein Neuling in der Sprache C. Wenn ich die Adresse der lokalen Variablen dem globalen Zeiger zuweise, was passiert? Wie,Weisen Sie dem globalen Zeiger in C die Adresse der lokalen Variablen zu?

#include <stdio.h> 

void func(); 
int *ptr; 

int main() 
{ 
    func(); 
} 

void func() 
{ 
    int i = 0; 
    ptr = &i; 
} 

Ist es richtig, die Adresse der lokalen Variablen dem globalen Zeiger zuzuweisen?

+1

undefiniertes Verhalten für Call-Expression nicht die Art der aufgerufenen Funktion entsprechen. – EOF

+1

Ihre Aufgabe ist korrekt; Nach Verlassen von 'func' existiert die Variable' i' jedoch nicht mehr und Sie haben von da an undefiniertes Verhalten. –

+0

Nachschlagen 'Dangling pointer' –

Antwort

1

Es macht einfach das, was Sie tun, es ist nichts falsch daran, außer dass es wahrscheinlich nicht das ist, was Sie wollen.

Es weist also nur die Adresse iptr an dem Punkt, den Sie zuweisen. Wenn Sie func verlassen, wird dieser Zeiger ungültig.

Hinweis Dieses Verhalten ist vollständig definiert: Die Adresse i an der Stelle, die Sie der globalen Variablen zuweisen, ist definiert, und Sie können sie zuweisen. Das Problem kommt erst später zum Tragen, wenn Sie versuchen, die Variable zu dereferenzieren, nachdem Sie die Funktion func verlassen haben. Solange Sie nur die globale Variable in func verwenden, gibt es kein Problem (außer dass eine globale Variable wirklich bedeutungslos ist).

An dieser Stelle existiert diese Variable nicht mehr. Und es ist sehr wahrscheinlich, dass Sie entweder einen segfault erhalten oder zumindest einige seltsame Zahlen erhalten (weil Sie den alten Stapelrahmen mit einigen anderen Werten überschrieben haben).


nur als Randnotiz: Was ich mit diesem Stack-Frame, was bedeuten. Sie können diesen Code versuchen, auf die meisten Compiler (ohne Optimierungen!)

#include <stdio.h> 
int *ptr; 

void f1() { 
    int i = 0; 
    ptr = &i; 
} 
void f2() { 
    int i = 1; 
} 

int main() { 
    f1(); 
    printf("%d\n", *ptr); 
    f2(); 
    printf("%d\n", *ptr); 
} 

Ohne Optimierungen, wird dies höchstwahrscheinlich

0 
1 

drucken Da die Variable i die gleiche Adresse haben, wenn f1 und f2 Aufruf von main().

Mit Optimierungen wird der Aufruf an f2() optimiert.

Immer noch: Dies ist undefiniertes Verhalten und muss nicht durchgeführt werden.

0

Ihre Syntax ist korrekt, aber die lokale Variable existiert nicht mehr, da sie in den Bereich des Codeblocks des Funktionsaufrufs gehört. Um dies zu beheben, ist eine Option, die lokale Variable statisch zu machen:

#include <stdio.h> 

void func(); 
int *ptr; 

int main() 
{ 
    func(); 
} 

void func() 
{ 
    static int i = 0; 
    ptr = &i; 
} 

Eine andere Möglichkeit wäre, neue Speicher innerhalb der Funktionsaufruf zuweisen, den globalen Zeiger auf die Adresse des neu zugewiesenen Speichereinstellung:

#include <stdio.h> 

void func(); 
int *ptr = NULL; 

int main() 
{ 
    func(); 
} 

void func() 
{ 
    if(ptr != NULL) 
     free(ptr); 
    int *i = (int *)malloc(sizeof(int)); 
    ptr = i; 
} 
0

Was Sie haben, ist syntaktisch korrekt, und der Code wie geschrieben ist semantisch gültig (aber ptr wird nie verwendet, ist es ein bisschen sinnlos).

Wenn Sie auf ptr zugreifen, wenn es einen Zeiger enthält, der den Gültigkeitsbereich überschritten hat, erhalten Sie undefiniertes Verhalten.

Betrachten Sie jedoch ein etwas größeres Codefragment. Hier ruft der Code, der ptr setzt, eine Funktion auf, die ptr verwendet, und die Variable, die ptr verweist, ist noch definiert, so dass es kein Problem gibt, den Zeiger zu verwenden.

Dies ist legitimer Code - obwohl die Verwendung globaler Variablen etwas ist, das Sie im Allgemeinen vermeiden sollten, und das vollkommen vermeiden könnte.

Beispielausgabe:

func: A 0 
ptr = 0x7fff55be74ac; *ptr = 0 
func: B 42 
main: A 20 
ptr = 0x7fff55be74cc; *ptr = 20 
main: B 42 
Verwandte Themen