2010-07-20 13 views
18

¿Por qué este código no es válido?typedef y especificadores de tipos no simples

typedef int INT; 
unsigned INT a=6; 

mientras que el código siguiente es válida

typedef int INT; 
static INT a=1; 

?

Según mi entender unsigned int no es un "simple type specifier" por lo que el código está mal formado. No estoy seguro sin embargo.

¿Alguien puede señalar la sección relevante del Standard que hace que el primer código no sea válido (y el segundo código sea válido)?

EDITAR

Aunque Johannes Schaub's respuesta parecía ser correcta y al punto (se había borrado su respuesta BTW) acepté la respuesta de James Curran para su corrección y precisión.

+0

Por curiosidad, ¿por qué harías eso? No hay muchas razones para esa redefinición. 'typedef unsigned int UINT;' podría tener más sentido, aunque .... – JAB

+1

Sí JAB Sé ​​que, en realidad, nunca escribiría ese código prácticamente. Sin embargo, tengo curiosidad por saber por qué no funciona el primer código. Entonces la pregunta también ha sido etiquetada 'language-lawyer'. –

+0

Sé que este no es el tema principal, pero puede escribir "std :: make_unsigned :: type" (vea http://msdn.microsoft.com/en-us/library/ee361636.aspx?ppud=4) – Tomaka17

Respuesta

29

typedef s no son como macros. No son solo una sustitución de texto. Un Typedef crea un nuevo nombre de tipo.

Ahora cuando dices unsigned int, el unsigned no es un modificador que se agrega al int. unsigned int es el nombre completo de tipo; simplemente sucede que tiene un espacio en él.

Por lo tanto, cuando diga typedef int INT;, entonces INT es el nombre completo. No puede ser modificado.

static (como const) es un especificador de clase de almacenamiento. En realidad, no es parte del nombre del tipo.

+1

C++ 0x sección estándar 3.9.1 párrafo 3 enumera los tipos integrales sin firmar y admite su respuesta. 'unsigned int' es un tipo que tiene un espacio en el nombre. 'unsigned' no está listado como un modificador a otro tipo para hacerlo mágicamente no negativo. –

12
  • 7.1.1: static es un especificador de clase de almacenamiento. Se puede colocar antes del de cualquier tipo.
  • 7.1.5: ¿qué es un especificador de tipo (sin firmar se puede combinar con char, largo, corto, o int)
+3

'unsigned' también puede ser un tipo por sí mismo. – torak

+0

Y califica implícitamente el tipo – Scharron

+0

+1 no muy elaborado, pero correcto y si tiene algún conocimiento de standardese, sospecho que estos números de sección lo ayudarán. –

2

No olvide que typedef-ing no es como la definición de macro; en su ejemplo, parece que si cree que su INT debe verse como un literal int. Desde el punto de vista del compilador, typedef define alias de tipo, pero esto no se ve a nivel de "sintaxis" (los tipos typedef-ed son como tipos "nativos" en el nivel de sintaxis); y dado que en ese nivel sin signo está permitido antes de char largo corto o int solamente, su unsigned INT se ve como un "tipo" ("diferente" de char, largo, corto, int) precedido por unsigned.

Cuestiones relacionadas