webentwicklung-frage-antwort-db.com.de

Statische Variable innerhalb einer Funktion in C

Was wird ausgedruckt? 6 6 oder 6 7? Und warum?

void foo()
{
    static int x = 5;
    x++;
    printf("%d", x);
}

int main()
{
    foo();
    foo();
    return 0;
}
94
Vadiklk

Hier gibt es zwei Aspekte: Lebensdauer und Umfang.

Im Bereich der Variablen kann der Variablenname angezeigt werden. Hier ist x nur in der Funktion foo () sichtbar.

Die Lebensdauer einer Variablen ist der Zeitraum, über den sie existiert. Wenn x ohne das Schlüsselwort static definiert wäre, würde die Lebensdauer vom Eintrag in foo () bis zur Rückkehr von foo () reichen. es würde also bei jedem Anruf auf 5 initialisiert.

Das Schlüsselwort static dient dazu, die Lebensdauer einer Variablen auf die Lebensdauer des Programms zu verlängern. z.B. Die Initialisierung erfolgt nur einmal und nur einmal, und die Variable behält ihren Wert bei allen zukünftigen Aufrufen von foo ().

143
user82238

Ausgabe : 6 7

Grund : Die statische Variable wird nur einmal initialisiert (im Gegensatz zur automatischen Variablen) und eine weitere Definition der statischen Variablen würde zur Laufzeit umgangen. Wenn es nicht manuell initialisiert wird, wird es automatisch mit dem Wert 0 initialisiert . 

void foo() {
    static int x = 5; // assigns value of 5 only once
    x++;
    printf("%d", x);
}

int main() {
    foo(); // x = 6
    foo(); // x = 7
    return 0;
}
37
Nitesh Borad

Das ist dasselbe wie das folgende Programm:

static int x = 5;

void foo()
{
    x++;
    printf("%d", x);
}

int main()
{
     foo();
     foo();
     return 0;
}

Alles, was das statische Schlüsselwort in diesem Programm tut, ist, dass es dem Compiler (im Wesentlichen) sagt: "Hey, ich habe hier eine Variable, auf die ich nicht will, dass jemand anderes auf sie zugreift.

Innerhalb einer Methode teilt das Schlüsselwort static dem Compiler das gleiche wie oben mit, aber auch: "Sagen Sie niemandem, dass dies außerhalb dieser Funktion existiert, es sollte nur innerhalb dieser Funktion zugänglich sein".

Ich hoffe das hilft 

9

6 7

der Compiler ordnet an, dass die Initialisierung statischer Variablen nicht bei jeder Eingabe der Funktion erfolgt

8
Chaim Geretz

Eine statische Variable innerhalb einer Funktion hat eine Lebensdauer, solange Ihr Programm ausgeführt wird. Es wird nicht jedes Mal zugewiesen, wenn Ihre Funktion aufgerufen und freigegeben wird, wenn Ihre Funktion zurückkehrt.

5
Donotalo

Vadiklk,

Warum ...? Der Grund dafür ist, dass die statische Variable nur einmal initialisiert wird und ihren Wert im gesamten Programm beibehält. Sie können die statische Variable zwischen Funktionsaufrufen verwenden. Außerdem kann sie gezählt werden, wie oft eine Funktion aufgerufen wird " 

main()
{
   static int var = 5;
   printf("%d ",var--);
   if(var)
      main();
} 

und die Antwort lautet 5 4 3 2 1 und nicht 5 5 5 5 5 5 .... (Endlosschleife), wie Sie es erwarten.................. Die statische Variable wird einmalig beim nächsten Aufruf von main () initialisiert es wird nicht auf 5 initialisiert, da es bereits im Programm initialisiert ist. So können wir den Wert ändern, aber nicht erneut initialisieren. So funktioniert statische Variable. 

oder Sie können als Speicher betrachten: statische Variablen werden im Datenabschnitt eines Programms gespeichert, und Variablen, die im Datenabschnitt gespeichert werden, werden einmalig initialisiert. und vor der Initialisierung bleiben sie im BSS-Bereich.

Auto (local) -Variablen werden wiederum im Stack gespeichert und alle Variablen im Stack werden immer neu initialisiert, wenn die Funktion als neuer FAR (Funktionsaktivierungsdatensatz) aufgerufen wird.

okay, für ein besseres Verständnis machen Sie das obige Beispiel ohne "statisch" und lassen Sie wissen, was die Ausgabe sein wird. Das lässt Sie den Unterschied zwischen diesen beiden verstehen.

Danke Javed

2
Javed

Die Ausgabe wird 6 7 sein. Eine statische Variable (ob innerhalb einer Funktion oder nicht) wird genau einmal initialisiert, bevor eine Funktion in dieser Übersetzungseinheit ausgeführt wird. Danach behält es seinen Wert, bis es geändert wird.

2
Jerry Coffin

6 und 7 Da die statische Variable nur einmal initialisiert wird, wird So wird 5 ++ beim ersten Aufruf 6 ++ wird beim zweiten Aufruf zu 7 Hinweis: Wenn der zweite Aufruf erfolgt, ist x der Wert 6 statt 5, da x eine statische Variable ist.

1
Tushar shirsath

Ausgabe: 6,7

Grund

Die Deklaration von x befindet sich in foo, aber die x=5-Initialisierung erfolgt außerhalb von foo!

Was wir hier verstehen müssen, ist das 

static int x = 5;

ist nicht das Gleiche wie

static int x;
x = 5;

Andere Antworten haben die wichtigen Wörter, Umfang und Lebensdauer verwendet und darauf hingewiesen, dass der Geltungsbereich von x von der Deklaration in der Funktion foo bis zum Ende der Funktion foo reicht. Ich habe zum Beispiel geprüft, indem ich die Deklaration an das Ende der Funktion verschoben habe, und x wird in der x++;-Anweisung nicht deklariert.

Der static int x (scope) -Teil der Anweisung gilt also tatsächlich dort, wo Sie sie lesen, irgendwo INNERHALB VON der Funktion und nur von dort aus, nicht darüber in der Funktion.

Der x = 5 (lifetime) Teil der Anweisung ist jedoch Initialisierung der Variablen und geschieht AUSSERHALB VON der Funktion als Teil des Programmladens. Die Variable x wird beim Laden des Programms mit dem Wert 5 geboren.

Ich habe dies in einem der Kommentare gelesen: "Auch der wirklich verwirrende Teil wird nicht angesprochen. Dies ist die Tatsache, dass der Initialisierer bei nachfolgenden Aufrufen übersprungen wird." Bei allen Aufrufen wird er übersprungen. Die Initialisierung der Variablen liegt außerhalb des eigentlichen Funktionscodes.

Der Wert 5 wird theoretisch festgelegt, unabhängig davon, ob foo überhaupt aufgerufen wird oder nicht, obwohl ein Compiler die Funktion möglicherweise wegoptimiert, wenn Sie ihn nirgendwo aufrufen. Der Wert 5 sollte vor dem Aufruf von foo in der Variablen stehen.

Innerhalb von foo generiert die Anweisung static int x = 5; wahrscheinlich überhaupt keinen Code.

Ich habe die Adresse gefunden, die x verwendet, wenn ich eine Funktion foo in ein Programm von mir schreibe, und dann (richtig) vermutete, dass dieselbe Position verwendet wird, wenn ich das Programm erneut ausführte. Der unten abgebildete Teilbildschirm zeigt, dass x vor dem ersten Aufruf von foo den Wert 5 hat.

 Break Point before first call to foo

1
user3070485

Lesen wir einfach den Wikipedia-Artikel zu statischen Variablen ...

Statische lokale Variablen: Variablen, die innerhalb einer Funktion als statisch deklariert sind, werden statisch zugewiesen, haben jedoch denselben Gültigkeitsbereich wie automatische lokale Variablen. Die Werte, die die Funktion während eines Aufrufs in ihre statischen lokalen Variablen einfügt, bleiben also auch beim erneuten Aufruf der Funktion vorhanden.

1
Andrew White

Sie erhalten 6 7 als gedruckt, da dies leicht zu testen ist, und das ist der Grund: Beim ersten Aufruf von foo wird die statische Variable x auf 5 initialisiert. Dann wird sie auf 6 erhöht und gedruckt.

Nun zum nächsten Aufruf von foo. Das Programm überspringt die Initialisierung der statischen Variablen und verwendet stattdessen den Wert 6, der x zuletzt zugewiesen wurde. Die Ausführung läuft normal ab und gibt Ihnen den Wert 7.

6 7

x ist eine globale Variable, die nur von foo () sichtbar ist. 5 ist der Anfangswert, wie er im .data-Abschnitt des Codes gespeichert ist. Jede nachfolgende Änderung überschreibt den vorherigen Wert. Im Funktionskörper wird kein Zuordnungscode generiert.

1
mouviciel

Wenn in C++ 11 der zum Initialisieren einer lokalen statischen Variablen verwendete Ausdruck kein 'constexpr' ist (vom Compiler nicht ausgewertet werden kann), muss die Initialisierung beim ersten Aufruf der Funktion erfolgen. Das einfachste Beispiel ist die direkte Verwendung eines Parameters, um die lokale statische Variable zu initialisieren. Daher muss der Compiler Code ausgeben, um zu erraten, ob der Aufruf der erste ist oder nicht, was wiederum eine lokale boolesche Variable erfordert. Ich habe ein solches Beispiel zusammengestellt und anhand des Assembly-Codes geprüft, ob dies der Fall ist. Das Beispiel kann so sein:

void f( int p )
{
  static const int first_p = p ;
  cout << "first p == " << p << endl ;
}

void main()
{
   f(1); f(2); f(3);
}

wenn der Ausdruck 'constexpr' ist, ist dies natürlich nicht erforderlich, und die Variable kann beim Laden des Programms initialisiert werden, indem ein Wert verwendet wird, der vom Compiler im Ausgabe-Assembly-Code gespeichert ist.

0
user5122888