2008-08-28 9 views
27

una pregunta relacionada con Regular cast vs. static_cast vs. dynamic_cast:C++ estilos de sintaxis fundido

Lo echó estilo de sintaxis preferís en C++? sintaxis

  • -estilo C reparto: (int)foo
  • C++ - estilo de sintaxis reparto: sintaxis static_cast<int>(foo)
  • constructor: int(foo)

Ellos pueden no traducirse en exactamente las mismas instrucciones (¿verdad?) pero su efecto debería ser el mismo (¿verdad?).

Si solo está alternando entre los tipos numéricos incorporados, encuentro que la sintaxis del molde de estilo C++ es demasiado detallada. Como antiguo codificador de Java, suelo usar la sintaxis del estilo C en su lugar, pero mi gurú local de C++ insiste en usar la sintaxis del constructor.

¿Qué opinas?

Respuesta

49

que es mejor la práctica nunca se utilizar C-estilo arroja por tres razones principales:

  • como ya se ha mencionado, la comprobación no se realiza aquí. El programador simplemente no puede saber cuál de los varios moldes se usa, lo que debilita el tipado fuerte
  • los nuevos moldes son intencionalmente visualmente llamativos. Como los moldes a menudo revelan una debilidad en el código, se argumenta que hacer moldes visibles en el código es algo bueno.
  • esto es especialmente cierto si se buscan moldes con una herramienta automatizada. Encontrar modelos de estilo C confiablemente es casi imposible.

Como palm3D señaló:

me parece C++ - sintaxis fundido estilo demasiado prolijo.

Esto es intencional, por las razones indicadas anteriormente.

La sintaxis constructor (nombre oficial: conversión de estilo de función) es semánticamente la misma como el reparto de estilo C y se debe evitar también (a excepción de las inicializaciones de variables en la declaración), por las mismas razones. Es discutible si esto debería ser cierto incluso para los tipos que definen constructores personalizados, pero en C++ efectivo, Meyers sostiene que incluso en esos casos, debe abstenerse de usarlos. Para ilustrar:

void f(auto_ptr<int> x); 

f(static_cast<auto_ptr<int> >(new int(5))); // GOOD 
f(auto_ptr<int>(new int(5));    // BAD 

El static_cast aquí realmente llamar al constructor auto_ptr.

+9

Me pregunto cuántas veces ha buscado un molde en su código con un herramienta automatizada ... – Blindy

+2

@Blindly: sucede. Ya he hecho eso. Recuerde que en C++, a diferencia de otros lenguajes (Java, C#), generalmente puede programar sin conversión. Cada lanzamiento explícito en su código es un defecto de diseño potencial. La identificación de moldes en su código C++ es un paso importante en la refactorización. En C# sería por supuesto ridículo buscar moldes en código, ¡están en todas partes! –

+0

@Konrad: Y, por supuesto, tanto Java * como * C# también tienen su propio equivalente de 'dynamic_cast', que es un elenco especial. – Puppy

1

sintaxis de conversión de estilo C, no verifique el error. C++ - sintaxis de estilo, realiza algunas comprobaciones. Al usar static_cast, incluso si no funciona, al menos debe saber que debe tener cuidado aquí.

+1

'static_cast' siempre comprueba que los tipos de origen y destino sean compatibles. (No puede proteger a los usuarios contra su error si convierten una base en un tipo derivado que realmente no tiene, pero es su culpa). –

11

Según Stroustrup:

El "nuevo estilo de moldes de" se introdujeron a dar a los programadores la oportunidad de exponer sus intenciones más claramente y para el compilador para capturar más errores.

Así que realmente, es por seguridad, ya que hace más tiempo de verificación en tiempo de compilación.

1

El estilo C es la peor manera de hacerlo. Es más difícil de ver, no se puede fusionar, combina diferentes acciones que no deberían fusionarse, y no puede hacer todo lo que pueden hacer las versiones de C++. Realmente deberían haber eliminado los moldes estilo C del idioma.

1

Uso static_cast por dos razones.

  1. Está explícitamente claro lo que está sucediendo. No puedo leer sobre eso sin darme cuenta de que hay un elenco pasando. Con moldes de estilo C su ojo puede pasar sin pausa.
  2. Es fácil buscar cada lugar en mi código donde estoy realizando el casting.
2

Definitivamente C++ - style. El tipeo adicional le ayudará a evitar el lanzamiento cuando no debería :-)

5

En relación con este tema, estoy siguiendo las recomendaciones hechas por Scott Meyers (More Effective C++, artículo 2: Prefiero moldes de estilo C++).

Estoy de acuerdo en que el estilo de C++ es detallado, pero eso es lo que me gusta de ellos: son muy fáciles de detectar y hacen que el código sea más fácil de leer (que es más importante que escribir).

También lo obligan a pensar qué tipo de elenco necesita y elegir el correcto, reduciendo el riesgo de errores. También lo ayudarán a detectar errores en tiempo de compilación en lugar de en tiempo de ejecución.

1

Actualmente usamos modelos de estilo C en todas partes. Le pregunté al otro casting question, y ahora veo la ventaja de usar static_cast en su lugar, aunque solo sea "greppable" (me gusta ese término). Probablemente comenzaré a usar eso.

No me gusta el estilo C++; se parece demasiado a una llamada de función.

+1

pareciendo una llamada a la función puede ser agradable, le permite tener funciones de utilidad que comparten el mismo estilo, como el 'lexical_cast' común para convertir de cadenas <-> tipos numéricos. Pero eso es solo una opinión. –

1

Vaya por el estilo C++ y, peor aún, los fragmentos de código verbosos feos que componen el encasillado explícito de C++ serán un recordatorio constante de lo que todos sabemos (es decir, el casting explícito es malo; el plomo en la acuñación de improperios) No vaya con el estilo C++ si desea dominar la técnica de seguimiento de errores de tiempo de ejecución.

1

La sintaxis del constructor. C++ es OO, existen constructores, los uso. Si siente la necesidad de anotar estos códigos de conversión, debe hacerlo para cada tipo, no solo para los integrados. Tal vez use la palabra clave "explícita" para los generadores de conversión, pero la sintaxis del cliente imita exactamente lo que hace la sintaxis del ctor para los tipos incorporados. Al ser greppable, eso puede ser cierto, pero qué gran sorpresa es que escribir más caracteres hace que las búsquedas sean más fáciles. ¿Por qué tratar estos como especiales? Si está escribiendo fórmulas matemáticas con muchos int/unsigned/... hacia y desde gráficos dobles/float, y necesita escribir un static_cast cada vez, el aspecto de la fórmula se llena y es muy ilegible. Y es una batalla cuesta arriba de todos modos, ya que muchas veces se convertirá sin siquiera darse cuenta de que lo es. Para los emisores de downcasting uso el static_cast ya que por supuesto no existe el ctor por defecto que haría eso.