2012-08-29 22 views
13

C++ Primer dicevariables estáticas locales y globales en C++

Cada variable estática local se inicia antes de la primera vez la ejecución pasa a través de la definición del objeto. Las estáticas locales son no destruidas cuando termina una función; se destruyen cuando finaliza el programa .

¿Las variables locales estáticas son diferentes de las variables estáticas globales? Aparte del lugar donde están declarados, ¿qué más es diferente?

void foo() { 
    static int x = 0; 
    ++x; 

    cout << x << endl; 
} 

int main (int argc, char const *argv[]) { 
    foo(); // 1 
    foo(); // 2 
    foo(); // 3 
    return 0; 
} 

comparar con

static int x = 0; 

void foo() { 
    ++x; 

    cout << x << endl; 
} 

int main (int argc, char const *argv[]) { 
    foo(); // 1 
    foo(); // 2 
    foo(); // 3 
    return 0; 
} 

Respuesta

18

Las diferencias son:

  • El nombre sólo es accesible dentro de la función, y no tiene ninguna vinculación.
  • Se inicializa la primera vez que la ejecución llega a la definición, no necesariamente durante las fases de inicialización del programa.

La segunda diferencia puede ser útil para evitar la estática intialisation fin fiasco, donde las variables globales se puede acceder antes de que se inicializan. Al reemplazar la variable global por una función que devuelve una referencia a una variable estática local, puede garantizar que se inicialice antes de que cualquier cosa acceda a ella. (Sin embargo, todavía no hay garantía de que no se destruirá antes de que algo termine de acceder a él, de todas maneras debe tener mucho cuidado si cree que necesita una variable accesible a nivel mundial. Consulte los comentarios de link para obtener ayuda en esa situación.)

+1

Puede garantizar el orden de destrucción con un poco de trabajo. http://stackoverflow.com/a/335746/14065 –

5

Su ámbito de aplicación es diferente. Una variable estática de ámbito global es accesible para cualquier función en el archivo, mientras que la variable con ámbito de función solo es accesible dentro de esa función.

+0

Sí, por supuesto. Gracias – JAM

+0

@ DavidRodríguez-dribeas: 'no está definido en la unidad de compilación ** s **. Dentro de una unidad de compilación, el orden está bien definido como el orden de la declaración. –

+0

@LokiAstari: Tiene razón ... Fui demasiado vago en el comentario :) –

4

Hay verdadero nombre es:

static storage duration object. 

Las variables globales son también 'objeto duración de almacenamiento estático'. La principal diferencia con respecto a las variables globales son:

  • Ellos no se inicializan hasta que el primer uso
    Nota: Una excepción durante la construcción significa que no se inicializan y por lo tanto no se utilizan.
    Se volverá a intentar la próxima vez que se ingrese la función.
  • Hay el visability está limitada por el alcance de
    (es decir, pueden no ser visto fuera de la función)

Aparte de que son sólo como 'objetos duración de almacenamiento estático' otro.

Nota: como todos los 'objetos de duración de almacenamiento estáticos' se destruyen en orden inverso a la creación.

+0

¿Estoy malinterpretando la especificación cuando la leí, ya que los locals estáticos _may_ pueden inicializarse junto con las otras estadísticas y no pueden retrasarse hasta la primera llamada ? (C++ 11 §6.7.4 parece reenviar a §3.6.2 para algunos casos y permite eso) –

+0

** 3.7.1 Duración de almacenamiento estático ** (Nota: 6.7 describe la inicialización de variables estáticas locales). ** 6.7 Declaración de declaración ** (La inicialización constante (3.6.2) de una entidad de ámbito de bloque con duración de almacenamiento estática, si corresponde, se realiza antes de que se ingrese por primera vez su bloque. De lo contrario, dicha variable se inicializa la primera vez el control pasa a través de su declaraciónInstalación constante (3.6.2) de una entidad de alcance de bloque con duración de almacenamiento estática, dicha variable se considera inicializada al finalizar su inicialización). –

1

La diferencia principal o más grave es el momento de la inicialización. Las variables estáticas locales se inicializan en la primera llamada para funcionar donde se declaran.Los globales se inicializan en algún punto en el tiempo antes de la llamada a la función principal; si tiene pocas variables estáticas globales, se inicializan en un orden no especificado, lo que puede causar problemas; esto se llama fiasco de inicialización estática.

0

En su primer bloque de código, x es local para la función foo() lo que significa que se creó en foo() y se destruyó al final de la función después de cout. Sin embargo, en su segundo bloque x es global lo que significa que el alcance de x es el programa completo. Si quería bajo int main su podría cout < < x < < endl y se imprimiría sin embargo, en el primer bloque sería decir x no declarado

0
  1. Se sabe que todas las funciones en un programa mientras mundial las variables son conocidas solo en un alcance limitado.
  2. Las variables estáticas globales se pueden inicializar antes de que comience el programa, mientras que las variables estáticas locales se pueden inicializar a medida que la ejecución llega al punto.
3

Afortunadamente, este ejemplo ayudará a comprender la diferencia entre la variable estática local y la variable global.

#include <iostream> 

using namespace std; 

static int z = 0; 

void method1() { 
    static int x = 0; 
    cout << "X : " << ++x << ", Z : " << ++z << endl; 
} 

void method2() { 
    int y = 0; 
    cout << "Y : " << ++y << ", Z : " << ++z << endl; 
} 

int main() { 
    method1(); 
    method1(); 
    method1(); 
    method1(); 
    method2(); 
    method2(); 
    method2(); 
    method2(); 
    return 0; 
} 

de salida:

X : 1, Z : 1 
X : 2, Z : 2 
X : 3, Z : 3 
X : 4, Z : 4 
Y : 1, Z : 5 
Y : 1, Z : 6 
Y : 1, Z : 7 
Y : 1, Z : 8 
Cuestiones relacionadas