Una matriz con destino debe ser una expresión constante integral, ver 8.3.4 [dcl.array]/1 (misma formulación en C++ 03 y C++ 11):
Si la expresión constante (5.19) está presente, será una expresión de constante integral y su valor será mayor que cero.
En C++ 03 una expresión constante integral no se puede inicializar mediante un literal flotante a no ser fundido a tipo integral, ver la última frase del 5,19 [expr.const]/1:
Un La expresión de constante integral puede implicar solo literales (2.13), enumeradores, const
variables o datos estáticos miembros de tipos integrales o de enumeración inicializados con expresiones constantes (8.5), parámetros de plantilla no tipo de tipos integrales o de enumeración y expresiones sizeof
. Los literales flotantes (2.13.3) solo pueden aparecer si se convierten a tipos integrales o de enumeración.
Esto significa que en C++ 03 i
no es una expresión de la constante integral, por lo que no se puede utilizar como una matriz unida.
GCC y Clang permiten matrices de longitud variable como una extensión a C++ 03, por lo que se compilan con un límite no constante, pero aparece una advertencia con -pedantic
. Cambio de inicializador de la constante de echarlo a los de tipo integral hace i
una expresión constante integral válida:
const int i = (int) 1.0;
Con que cambiar la matriz ya no es de longitud variable y no hay ninguna advertencia incluso con -pedantic
.
En C++ 11 5.19 [expr.const]/3 dice:
A literal expresión constante es un núcleo de expresión constante prvalue de tipo literal, pero no Tipo de puntero. Una expresión constante integral es una expresión constante literal del tipo de enumeración integral o no codificado.
El precedente (bastante largos) párrafos describen las reglas para expresiones constantes de núcleo, pero básicamente en C++ 11 el doble inicializador no impide i
ser una expresión constante núcleo, incluso sin una conversión, por lo que es una expresión de constante integral y, por lo tanto, una matriz válida vinculada, por lo que no hay advertencia.
¿Querías hacer 'i' a double, not an int? – David
@Dave: No, eso fue a propósito. Ver el enlace a la pregunta anterior. –
FWIW, clang ++ 3.0 no muestra la advertencia VLA. No tengo g ++ para probarlo, pero supongo que la advertencia no desaparece si cambia la asignación a 'const int i = 1;'. ¿Lo hace? – jweyrich