2010-09-07 29 views
6
int val = 5; 

printf("%d",++val++); //gives compilation error : '++' needs l-value 

int *p = &val; 
printf("%d",++*p++); //no error 

¿Podría alguien explicar estos 2 casos? Gracias.Explicación de ++ val ++ y ++ * p ++ en C

+0

En casos como este, a menudo ayuda a publicar también los mensajes de error que está viendo y el compilador (versión) que estás utilizando. – sbi

+7

Nadie debería escribir código como este. – duffymo

+0

Vota para cerrar porque no es una pregunta real. Código como este no se encuentra en la vida real. Cualquier cosa que sea simplemente un accidente de sintaxis como esta debería apuntar a las preguntas frecuentes que solo dicen que no seas tonto. –

Respuesta

27

++val++ es lo mismo que ++(val++). Como el resultado de val++ no es un valor l, esto es ilegal. Y como señaló Stephen Canon, si el resultado de val++ fuera un valor l, ++(val++) sería un comportamiento indefinido ya que no hay punto de secuencia entre ++ s.

++*p++ es lo mismo que ++(*(p++)). Como el resultado de *(p++)es y lvalue, esto es legal.

+1

Excelente respuesta, aunque me gustaría señalar que incluso si 'val ++' fuera un lvalue, el comportamiento aún no está definido. '(++ val) ++' en C++, por ejemplo, invocaría un comportamiento indefinido. –

+0

@Stephen: Muy buen punto, lo agregaré a la respuesta. – sepp2k

+1

El operador posterior al incremento siempre devuelve un 'rvalue' (tanto en C como en C++). En C++, '(++ val) ++' invoca un comportamiento indefinido porque el operador de preincremento ('++') devuelve un lvalue (en C++) y el valor de 'val' se modifica más de una vez entre dos puntos de secuencia . –

0

int j = ++val++; //gives compilation error

Eso porque no se puede pre-incremento de un rvalue. ++val++ se interpreta como ++(val++) porque el operador de incremento adicional tiene una precedencia mayor que el operador de incremento previo. val++ devuelve rvalue y el operador de preincremento requiere que su operando sea lvalue. :)

int k = ++*p++; //no error

++*p++ se interpreta como ++(*(p++)), que es perfectamente válido.

4

La expresión ++val++ es la misma que (++val)++ (o quizás ++(val++), de todos modos no es muy relevante). El resultado del operador ++ no es la variable, sino el valor, y no puede aplicar el operador a un valor.

La expresión ++*p++ es la misma que ++(*(p++)). El resultado es p++, pero el resultado de *(p++) es una ubicación de memoria a la que se puede aplicar el operador ++.

+0

'++ val ++' es lo mismo que '++ (val ++)', que ** no ** es lo mismo que '(++ val) ++'. (Aunque en C, ambos son sintácticamente inválidos) –

+0

@Stephen Canon: Sí, simplemente no es obvio a cuál evalúa. Como la expresión no es válida, nunca me molesté en saber cuál de las dos variantes inválidas es.:) – Guffa

+0

ah, pero en C++, uno de ellos no es válido mientras que el otro es sintácticamente válido pero semánticamente indefinido. (C++ es loco!) –

1

también en cuenta que se está cambiando la dirección del puntero por

int k = ++*p++; 
+0

sí, lo sé. Lo usé por simplicidad. En lugar de int val, podría haber usado int array. – understack