2014-04-10 18 views
13

folgenden Codebeispiel vor:Initialisierung der statischen Variablen mit sich selbst

#include <iostream> 

static int bar = bar; 

int main() 
{ 
    int foo = foo; 
    std::cout << "foo = " << foo << std::endl; 
    std::cout << "bar = " << bar << std::endl; 
} 

ich folgende Compiler-Warnung erhalten:

main.cpp: In function 'int main()': 
main.cpp:7:15: warning: 'foo' is used uninitialized in this function [-Wuninitialized] 
    int foo = foo; 
      ^

Ausgang:

foo = 0 
bar = 0 

ich diese Warnung zu erwarten als foo verwendet uneinheitlich. Anstelle von 0 kann 'foo' alles sein. Die Selbstzuweisung ist nicht definiert.

Aber warum ist die Selbstzuweisung von 'bar' nicht gewarnt? Ist diese Zuordnung von 'bar' definiert oder undefiniert und warum?

Ich weiß, statische Variablen von Elementar-Datentypen werden mit '0' initialisiert, aber in diesem Fall wird die Variable 'bar' während ihrer Initialisierung verwendet. Ich frage mich, ob dies definiertes Verhalten ist und die '0' die erwartete Ausgabe ist. (Das würde erklären, dass keine Compiler-Warnung auftritt).

Link to Live example

+0

Die statische Initialisierung hat mehr als eine Phase. – chris

+0

Wahrscheinlich, weil statische Variablen im globalen Gültigkeitsbereich immer Null-initialisiert sind, so dass der Compiler weiß, dass "bar" vor der Zuweisung effektiv "0" ist. –

+1

@ FrédéricHamidi: Beachten Sie, dass sie nicht null-initialisiert, sondern standardmäßig konstruiert sind. Das macht einen Unterschied für Strukturen/Klassen! – anderas

Antwort

14

Ich glaube, dass ein Teil des Standard auf Ihre Frage relevant ist (§3.6.2/2):

Variablen mit statischer Speicherdauer (3.7.1) oder Fadenspeicherdauer (3.7.2) beträgt Null initialisiert (8,5) , bevor eine andere Initialisierung stattfindet. [...]

Also in diesem Fall, noch bevor der Compiler bei Ihrer Definition sieht von bar, hat es bereits Null initialisiert.

Da es im Standard etwas weiter spezifiziert ist, sollte es zwei Phasen für die Initialisierung der statischen Variablen geben (Hervorhebung meins).

Zusammen werden Null-Initialisierung und Konstanten Initialisierung statische Initialisierung; Alle anderen Initialisierung ist dynamische Initialisierung. Die statische Initialisierung muss durchgeführt werden, bevor eine dynamische Initialisierung stattfindet.

Verwandte Themen