palabra clave estática en el archivo hy enlace interno
-
28-09-2019 - |
Pregunta
Sin embargo, otra cuestión static
.
He leído lo siguiente:
- ¿Cuáles son las variables estáticas?
- y estático flota
- http://msdn.microsoft.com/en-us/library /s1sb61xd.aspx
Y todavía no entiendo el siguiente comportamiento:
Tengo un archivo de h
:
// StaticTest.h
#include <stdio.h>
static int counter = 0;
struct A {
A () {
counter++;
printf("In A's ctor(%d)\n", counter);
}
~A () {
counter--;
printf("In A's dtor(%d)\n", counter);
}
};
static A a;
y dos archivos cpp
:
// StaticTest1.cpp
#include "StaticTest.h"
int main () {
return 0;
}
Y:
// StaticTest2.cpp
#include "StaticTest.h"
La salida del programa es:
In A's ctor(1)
In A's ctor(2)
In A's dtor(1)
In A's dtor(0)
Ahora, el constructor de A
se llama dos veces, ya que el archivo se incluye h
dos veces, y ya instancia con nombre de A
a
se declara static
, que tiene enlace interno y el compilador es feliz.
Desde el counter
también se declara estático, sino que también tiene enlace interno, y yo esperaría que su valor no será compartida en los dos archivos cpp
--- pero la salida del programa implica el valor es compartido, ya que cuenta con hasta 2.
cualquier idea?
EDIT:
Cualquier respuesta con respecto a lo que se considera un "buen hábito de programación" en el contexto de la declaración de variables estáticas en h
cpp
archivos vs. también se da la bienvenida.
Solución
Si StaticTest.h
se comparte entre los archivos de origen diferencia por lo que recibirá un comportamiento indefinido.
Si se define una clase o en línea funciones en diferentes unidades de traducción a continuación, sus definiciones debe ser el mismo (misma secuencia de tokens) y, fundamentalmente, cualesquiera identificadores deben referirse a la misma entidad (a menos que un objeto const
con enlace interno) como en la definición en otra unidad de traducción.
violar este porque counter
tiene enlace interno por lo que en diferentes unidades de traducción el identificador en las definiciones de función se refiere a un objeto diferente.
Referencia: C ++ 03 3,2 [basic.def.odr] / 5
.