2008-09-29 31 views
39

¿Qué hace el siguiente código en C/C++?¿Qué hace el operador de coma?

if (blah(), 5) { 
    //do something 
} 
+2

una pregunta muy cargado. +1 – jop

+0

Huele a tarea. – jfm3

+0

Debe especificar el idioma en la pregunta; No creo que etiquetar sea suficiente, incluso si esto no tiene etiquetas C y C++. –

Respuesta

66

operador coma se aplica y el valor 5 se utiliza para determinar la de condicional verdadero/falso.

Ejecutará blah() y recuperará algo (presumiblemente), luego se empleará el operador de coma y 5 será lo único que se usará para determinar el valor verdadero/falso de la expresión.


Nota que el, operador podría estar sobrecargado para el tipo de retorno de la función bla() (que no se ha especificado), haciendo que el resultado no es evidente.

+0

Curiosamente (al menos para mí), es evidente que el orden de las operaciones no está garantizado cuando se sobrecarga el operador de coma. En general, no creo que alguna vez lo haga. – itsmatt

+0

Eso es interesante ... –

+0

Me recuerda a un insecto que escribí hace un par de días: quería escribir un CAnObject (d, f); pero terminó escribiendo CAnObject a = (d, f); Desafortunadamente hubo una conversión del tipo f a CAnObject. Awch. – QBziZ

1

Yo diría que depende de blah().

+0

se llamará blah() y no conocemos los efectos secundarios. Entonces, respondiendo a la pregunta "¿qué hará este código?" no es posible. –

+0

Estoy de acuerdo contigo, Ben. No hay suficiente información para decir con certeza. – itsmatt

+0

por ejemplo, excepciones. O si prefiere c, goto. – tfinniga

45

Si el operador coma no está sobrecargado, el código es similar a esto:

blah(); 
if (5) { 
    // do something 
} 

Si se sobrecarga el operador coma, el resultado se basa en esa función.

#include <iostream> 
#include <string> 

using namespace std; 

string blah() 
{ 
    return "blah"; 
} 

bool operator,(const string& key, const int& val) { 
    return false; 
} 

int main (int argc, char * const argv[]) { 

    if (blah(), 5) { 
     cout << "if block"; 
    } else { 
     cout << "else block"; 
    } 

    return 0; 
} 

(editado para mostrar operador coma sobrecarga escenario. Gracias a David Pierre por sus comentarios sobre este)

+0

n, C++ tiene operador, a tener en cuenta aquí –

+0

Sí - olvidado que se puede anular el operador coma en C++. ¡Creo que ese es el verdadero objetivo de esta pregunta! – jop

0

Lo siguiente fue escrito asumiendo que es el código C, ya sea en un fichero C o dentro de un C bloque de un archivo de C++:

No tiene sentido si. Llamará a blah(), sin embargo, el resultado de blah() no es considerado por si en absoluto. Lo único que se considera es 5, por lo tanto, el if siempre se evaluará como verdadero. OIA se podría escribir este código como

blah(); 
// do something 

sin ningún si en absoluto.

+0

Sí, lamentablemente alguien podría haber devuelto un objeto blah() cuya clase había sobrecargado al operador de coma y quién sabe exactamente qué sucederá. El operador de coma podría comparar algo con el 5 y devolver falso, omitiendo el código entre corchetes por completo. – itsmatt

+0

Si es C++ en absoluto (incluso un proyecto C++ podría tener un archivo C simple entre la lista de archivos); hay una etiqueta C++, pero también una etiqueta C, y esto también podría estar dentro de un bloque externo "C", en cuyo caso no es posible la sobrecarga. – Mecki

13

En el caso patológico, depende de lo que haga el operador coma ...

class PlaceHolder 
{ 
}; 

PlaceHolder Blah() { return PlaceHolder(); } 

bool operator,(PlaceHolder, int) { return false; } 

if (Blah(), 5) 
{ 
    cout << "This will never run."; 
} 
20

Yo sé una cosa que este tipo de código debe hacer: debe hacer el codificador disparado. Tendría mucho miedo de trabajar al lado de alguien que escribe así.

1

En una respuesta más amplia. El operador de coma (sin sobrecarga) se resuelve como en, ejecuta la primera parte y devuelve la segunda parte.

Así que si tiene (foo(), bar()) Ambas funciones se ejecutarán, pero el valor de la expresión se evalúa como bar() (y el tipo de la expresión también).

Si bien no voy a decir que hay usos justos para eso, generalmente se considera un código un poco difícil de leer. Principalmente porque no hay muchos idiomas que compartan dichos constructos. Así que, como regla general personal, lo evito a menos que agregue código a una expresión preexistente y no quiera cambiar completamente su formato.

Ejemplo: Tengo una macro (no discutir si debe usar macros o no, a veces ni siquiera es usted que lo escribió)

FIND_SOMETHING (X) (X> 2)? find_fruits (x): find_houses (x)

Y generalmente lo uso en asignaciones como my_possession = FIND_SOMETHING (34);

Ahora quiero añadir registro a la misma para fines debuggin pero no puede cambiar las funciones hallazgo ,. Que podía hacer:

FIND_SOMETHING (X) (X> 2)? (LOG ("buscando frutas"), find_fruits (x)) :(LOG ("buscando casas"), find_houses (x))

0

Uso a veces construcciones como esta con fines de depuración. Cuando fuerzo el if close para ser cierto independientemente del valor de retorno de bla. Es obvio que nunca debería aparecer en el código de producción.