2010-01-31 16 views
49

Me pregunto cuál es la diferencia entre usar un const estático y un enum cuando se utilizan técnicas de metaprogramación de plantillas.Metaprogramación de la plantilla: diferencia entre utilizar Enum Hack y Static Const

EX: (Fibonacci través TMP)

template< int n > struct TMPFib { 
    static const int val = 
    TMPFib< n-1 >::val + TMPFib< n-2 >::val; 
}; 

template<> struct TMPFib<1> { 
    static const int val = 1; 
}; 

template<> struct TMPFib<0> { 
    static const int val = 0; 
}; 

vs

template< int n > struct TMPFib { 
    enum { 
    val = TMPFib< n-1 >::val + TMPFib< n-2 >::val 
    }; 
}; 

template<> struct TMPFib<1> { 
    enum { val = 1 }; 
}; 

template<> struct TMPFib<0> { 
    enum { val = 0 }; 
}; 

Por qué utilizar uno sobre el otro? He leído que el enum hack se usó antes de que la static const fuera admitida dentro de las clases, pero ¿para qué usarlo ahora?

+0

+1: una gran pregunta de hecho, y también me gustaría ver cuáles serán las respuestas, excepto por lo obvio. –

+2

const estático permite tipos distintos de int. doble por ejemplo. –

Respuesta

34

enumeraciones no lvals, valores de los miembros estáticos son y si pasa por referencia la plantilla será instanciado:

void f(const int&); 
f(TMPFib<1>::value); 

Si usted quiere hacer cálculos de tiempo de compilación pura etc. Esto es un efecto secundario no deseado .

La principal diferencia histórica es que las enumeraciones también funcionan para compiladores en los que no se admite la inicialización en clase de los valores de los miembros, esto debería corregirse ahora en la mayoría de los compiladores.
También puede haber diferencias en la velocidad de compilación entre enum y consts estáticos.

Hay algunos detalles en el boost coding guidelines y older thread en los archivos de impulso relacionados con el tema.

12

Para algunos, el anterior puede parecer menos pirata y más natural. También tiene memoria asignada por sí misma si usa la clase, por lo que puede, por ejemplo, tomar la dirección de val.

Este último es mejor soportado por algunos compiladores anteriores.

+0

Gracias. Exactamente el tipo de respuesta que estaba buscando. – Anonymous

+1

Personalmente estoy completamente en desacuerdo. Entonces la versión enum parece más natural. ¿Por qué hay una necesidad de una variable física? Enum es la representación de un valor constante. Usar una constante estática int parece más bien dar un paso atrás al tiempo en que tuvimos que usar macros para representar valores constantes. –

+2

@Martin, ¿qué tiene que ver la enumeración de palabras clave con el cálculo? Pero punto: todos pueden tener su propio punto sobre eso. –

1

En la otra cara de la respuesta @Georg, cuando una estructura que contiene una variable estática const se define en una plantilla especializada, debe declararse en la fuente para que el enlazador pueda encontrarla y darle una dirección a ser referenciado por. Esto puede causar innecesariamente (dependiendo de los efectos deseados) un código poco elegante, especialmente si intenta crear una biblioteca solo de encabezado. Puede resolverlo convirtiendo los valores a funciones que devuelven el valor, lo que también podría abrir las plantillas a la información de tiempo de ejecución.

Cuestiones relacionadas