Disponible la nueva versión "donationware" 7.3 de OrganiZATOR
Descubre un nuevo concepto en el manejo de la información.
La mejor ayuda para sobrevivir en la moderna jungla de datos la tienes aquí.

Curso C++

[Home]  [Inicio]  [Índice]


4.1.11b  Subespacio anónimo


§1  La gramática de C++ permite definir subespacios anónimos. Para esto se utiliza la palabra namespace sin ningún identificador antes del corchete de apertura:

namespace {   // subespacio anónimo

   ...        // Declaraciones }


§2  Todos los subespacios anónimos de ámbito global (no anidados) de la misma unidad de compilación comparten el mismo espacio de nombres. Es decir, además de los posibles subespacios nominados existe otro único, de los sin nombre.  Ejemplo:

namespace {      // subespacio anónimo
  int x;
}
namespace ALFA { // subespacio nominado
  int x;         // esta x es distinta de la anterior
}
namespace {      // subespacio anónimo (ampliación del primero)
  int y;
  int x;         // Error: declaración duplicada
}


§3  Todas las variables declaradas en el subespacio anónimo son conocidas en todo el ámbito del fichero, a no ser que otra definición posterior las oculte [1]. Sin embargo, los subespacios anónimos de las diferentes unidades de compilación son independientes, y no existe forma de acceder a un elemento del subespacio anónimo de un fichero desde otro fichero [2].  Considere los resultados del siguiente ejemplo:

#include <iostream>
  using namespace std;

namespace {           // subespacio anónimo
   int x = 1;
}
namespace ALFA {      // subespacio nominado
   int y = 10
}
 
void main (void) {    // ====================
   {
     int x = 2;
     cout << "X = " << x << << endl;   // Ok.
   }
   cout << "X = " << x << endl;        // Ok.
   cout << "Y = " << y << endl;        // M.6: Error!!
   cout << "Y = " << ALFA::y << endl;  // M.7: Ok.
}


En M.7 se obtiene un error:  Undefined symbol 'y' in function main, ya que la variable y del subespacio ALFA no es conocida desde el exterior a no ser que se incluya un especificador explícito, como es el caso de la línea M.7. En cambio, la variable x del subespacio anónimo es automáticamente conocida en el fichero sin necesidad de un especificador explícito.

Una vez eliminada la sentencia errónea, la salida es:

X = 2
X = 1
Y = 10


  La compartimentación antes aludida entre los miembros de subespacios anónimos de diferentes ficheros, permite hacer declaraciones estáticas sin utilizar el especificador static ( 4.1.8c), es decir, variables o funciones de ámbito global que solo sean conocidas en el fichero en que son declaradas.

Ejemplo: supongamos un programa compuesto por dos ficheros fuente: Fuente1.C y Fuente2.C

En el fichero Fuente1.C

#include <iostream>
extern void func(void);    // func está definida en Fuente2.C
namespace {                // Subespacio anónimo
   float pi = 3.14;        // pi es conocido solo en este fichero
}
int main() {
   float pi = 0.1;         // este pi es distinto del anterior
   std::cout << "pi = " << pi << std::endl;
   func();                 // llamada a func (definida en algún sitio)
   return 0;
}

En el fichero Fuente2.C

#include <iostream>
namespace {                // Subespacio anónimo
   float pi = 10.01;       // pi es conocido solo en este fichero
   void func(void) {       // func es conocida solo en este fichero
       std::cout << "Versión local de func(): pi = " << pi;
   }
}
void func(void) {          // puede ser conocida en otros ficheros
   std::cout << "Versión global de func(): pi = " << pi;
}

Salida del programa:

pi = 0.1 
Versión global de func(): pi = 10.01

  Inicio.


[1]  Como si al principio del fichero existiera una directiva using ( 4.1.11c) relativa al subespacio anónimo. En el ejemplo anterior es como si el subespacio anónimo se sustituyera por:

namespace ANONIMO {
  int x = 1;
}
using ANONIMO;

[2]  Precisamente la garantía de esta compartimentación es una de las posibles razones de utilización de subespacios anónimos.