2011-01-24 9 views
5

He leído en muchos lugares, pero realmente no puedo entender el comportamiento especificado en condicionales.Operador de coma en un condicional

Entiendo que en asignaciones evalúa el primer operando, descarta el resultado, luego evalúa el segundo operando.

Pero, para este código, ¿qué se supone que debe hacer?

CPartFile* partfile = (CPartFile*)lParam; 
ASSERT(partfile != NULL); 
bool bDeleted = false; 
if (partfile,bDeleted) 
    partfile->PerformFileCompleteEnd(wParam); 

El archivo parcial en el IF era un argumento innecesario, o tiene algún significado?

+0

Tal vez esto ayudará a: http://stackoverflow.com/questions/54142/c-comma-operator –

+0

Una posibilidad es que el codificador significó 'if (partfile && bDeleted)', algunos otros lenguajes de programación tienen 'IF a, b' para significar" si ayb " –

Respuesta

9

En este caso, es una expresión innecesaria, y se puede eliminar sin cambiar el significado del código.

+3

El operador de coma es reemplazable. Tal vez usarlo puede cambiar el estado de la expresión de la mano izquierda. – Benoit

+0

@Benoit No se puede sobrecargar para dos tipos primitivos (puntero y bool en este caso); al menos un operando debe tener el tipo de clase –

4

El operador de coma realiza la expresión del primer elemento, descarta los resultados y luego evalúa el resultado como la última expresión.

Así partfile,bDeleted habría evaulate lo habría partfile, descarta ese resultado, a continuación, evaluar y volver bDeleted

Es útil si se necesita para evaluar algo que tiene un efecto secundario (por ejemplo, llamar a un método). En este caso, sin embargo, es inútil.

Para obtener más información, ver se evalúa Wikipedia: Comma operator

+0

El operador de coma no evalúa los n-1 elementos. Todos los operadores en C/C++ son unarios o binarios. Si coloca varios operadores de coma en una línea, evaluará el primer elemento, lo descartará, evaluará el segundo elemento y utilizará el segundo elemento como operando para el siguiente operador de coma en la línea. Por supuesto, el resultado será el mismo que si evaluara n-1 elementos, pero para entender por qué, necesita saber qué está pasando entre ellos para llegar al último elemento. – Lundin

+0

buen punto, estaba pensando que a, b, c era un término (¿es esa la redacción correcta?), Pero eso no es cierto porque hay dos operadores de coma allí. publicación fija – helloworld922

1

PartFile, entonces bDeleted se evalúa y se utiliza como la prueba. Como la evaluación de partfile no tiene ningún efecto secundario, eliminarlo del condicional no tiene ningún efecto.

+0

Lo tiene al revés, el archivo parcial se evalúa e ignora y bDeleted se evalúa y se devuelve. – helloworld922

+0

@ helloworld922: tan cierto, lo arreglaré. – ThomasMcLeod

2
bool bDeleted = false; 
if (partfile,bDeleted) 
    partfile->PerformFileCompleteEnd(wParam); 

En este caso, la declaración if evalúa PartFile, bDeleted, pero bDelete siempre es falsa, por lo que la expresión no se puede ejecutar. La pregunta clave es "¿qué es todo eso?". La respuesta probable es que alguien haya querido evitar temporalmente que se ejecute la instrucción partfile->PerformFileCompleteEnd(wParam);, tal vez porque estaba causando algún problema o si deseaba garantizar que el código posterior informara los errores correctamente si ese paso no se realizaba. Para que recuerden cómo era el código, dejaron la antigua lógica "if (partfile)" allí, pero agregaron una variable bDeleted codificada para documentar que la lógica partfile->Perform... había sido efectivamente "eliminada" del programa.

Una mejor manera de desactivar temporalmente dicho código es probablemente ...

#if 0 
    if (partfile) 
     partfile->PerformFileCompleteEnd(wParam); 
#endif 

... aunque a veces trato de documentar el razonamiento también ...

#ifndef DONT_BYPASS_FILE_COMPLETE_PROCESSING_DURING_DEBUGGING 
    if (partfile) 
     partfile->PerformFileCompleteEnd(wParam); 
#endif 

... o ...

if (partFile, !"FIXME remove this after debugging") 
    partfile->PerformFileCompleteEnd(wParam); 

La mejor opción depende de su conjunto de herramientas y hábitos existentes (por ejemplo, algunos editores resalte "ARREGLAME" y "TODO" en video inverso por lo que es difícil pasar por alto o gris #if 0 bloques; es posible que tengas ciertas cuerdas que advierte sobre el control de origen; el preprocesador define solo en versiones de depuración frente a versiones de lanzamiento puede evitar la distribución accidental, etc.).

1

El operador de coma es una característica bastante oscura de C/C++. No debe confundirse con la coma en las listas de inicialización (es decir: int x, int y;) ni con la coma de separación de parámetros de llamada de función (es decir: func (x, y)).

El operador de coma tiene un único propósito: dar al programador un orden de evaluación garantizado de una expresión. Para casi todos los operadores en C/C++, el orden de evaluación de las expresiones no está definido. Si escribo

resultado = x + y;

donde xey son subexpresiones, entonces x o y pueden evaluarse primero. No puedo saber cuál, depende del compilador. Sin embargo, si escribe

result = x, y;

el orden de evaluación está garantizado por la norma: primero a la izquierda.

Por supuesto, los usos de este en aplicaciones del mundo real son bastante limitados ...