2012-05-24 16 views
14

tengo código C++ 03 que tiene este aspecto:Importación de std :: tr1 en std: ¿es legal? ¿Mejora la portabilidad?

#include <boost/tr1/unordered_map.hpp> 
... 
std::tr1::unordered_map<std::string, int> mystuff; 
... 

me empecé a preguntar que iba a sufrir más tarde si/cuando convierto mi código a 11 C++, que (supongo) doesn' t tiene std::tr1::unordered_map pero tiene std::unordered_map en su lugar. Así me ocurrió con este truco:

namespace std 
{ 
    using namespace ::std::tr1; 
} 
... 
std::unordered_map<std::string, int> mystuff; // no tr1 now! 
... 

¿Es legal (está prohibida la importación de tal cosas en std)? ¿Hará más fácil el puerto/interoperar con el código C++ 11?

+1

Mi compilador (VS2010) todavía entiende 'std :: tr1' aunque ahora todo también existe en' std'. – Benj

Respuesta

16

No debe tocar el espacio de nombres std: incluso si funciona ahora, puede causar dolores de cabeza severos más adelante (con una nueva versión del compilador, en un compilador diferente, etc.).

Actualización: Presupuesto de la norma (C++ 2003, sección 17.4.3.1 "nombres reservados") (encontrado here):

Es indefinido para un programa en C++ para añadir declaraciones o las definiciones de namespace std o espacios de nombres dentro del espacio de nombres std a menos que se especifique lo contrario. Un programa puede agregar especializaciones de plantilla para cualquier plantilla de biblioteca estándar al espacio de nombres std. Tal especialización (completa o parcial) de una plantilla de biblioteca estándar da como resultado un comportamiento indefinido a menos que la declaración dependa de un tipo de enlace externo definido por el usuario y a menos que la especialización cumpla con los requisitos de la biblioteca estándar para la plantilla original. [El énfasis es mío]

+1

Creo que las únicas respuestas interesantes son aquellas respaldadas por algunos hechos, como "lo que dice la norma sobre eso". – akappa

+0

@akappa - ver actualización – Attila

+0

ahora es mucho mejor (upvoted) – akappa

7

Importación cosas en ::std está prohibido por C++ 11 17.6.4.2.1:

El comportamiento de un programa en C++ no está definido si se agrega declaraciones o las definiciones de espacio de nombres std o a un espacio de nombre dentro del espacio de nombres std a menos que se especifique lo contrario.

3

Creo que this question es muy similar a lo que pregunta.

En particular, me gusta la respuesta que dice "usar autoconf para detectar símbolos disponibilidad y luego usar un alias define condicionales para el espacio de nombres derecha con un nombre dado".

1

Este tipo de portabilidad solo debe intentarse si tiene una prueba de que no puede soportar una biblioteca en particular de una manera más clara, e idealmente debe rodearlo con #ifdef s específico para ese entorno en particular.

El objetivo de tr1 era aislar su std de las cosas en tr1.

Cuestiones relacionadas