¿Es una mala práctica volver desde dentro de un try catch finalmente bloquear?


Así que me encontré con un código esta mañana que se veía así:

try
{
    x = SomeThingDangerous();
    return x;
}
catch (Exception ex)
{
    throw new DangerousException(ex);
}
finally
{
    CleanUpDangerousStuff();
}

Ahora bien, este código compila bien y funciona como debería, pero simplemente no se siente bien regresar desde dentro de un bloque de prueba, especialmente si finalmente hay un asociado.

Mi principal problema es lo que sucede si finalmente lanza una excepción de su propia? Tienes una variable devuelta, pero también una excepción para tratar... así que estoy interesado en saber lo que otros piensan acerca de volver desde dentro de un intento ¿block?

Author: Luke Girvin, 2009-01-16

6 answers

No, no es una mala práctica. Poner return donde tiene sentido mejora la legibilidad y el mantenimiento y hace que su código sea más fácil de entender. No debería importarle, ya que el bloque finally se ejecutará si se encuentra una instrucción return.

 157
Author: Mehrdad Afshari,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2009-10-02 20:35:22

Finalmente se ejecutará sin importar qué, por lo que no importa.

 16
Author: Ed S.,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2018-01-30 23:17:08

Personalmente, evitaría este tipo de codificación, ya que no tengo ganas de ver declaraciones de retorno antes de finalmente declaraciones.

Mi mente es simple y procesa las cosas de manera bastante lineal. Por lo tanto, cuando camino a través del código para el funcionamiento en seco, tenderé a pensar que una vez que pueda llegar a la declaración de retorno, todo lo que siga no importa, lo que obviamente está bastante mal en este caso (no es que afectaría a la declaración de retorno, pero lo que los efectos secundarios podrían ser).

Por lo tanto, organizaría el código para que la instrucción return siempre aparezca después de las instrucciones finally.

 14
Author: Conrad,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2009-01-16 04:14:28

Esto puede responder a su pregunta

¿Qué sucede realmente en una sentencia try { return x; } finally { x = null;}?

Al leer esa pregunta, parece que puede tener otra estructura try catch en la instrucción finally si cree que podría generar una excepción. El compilador averiguará cuándo devolver el valor.

Dicho esto, podría ser mejor reestructurar su código de todos modos solo para que no lo confunda más tarde o a alguien más que puede ser inconsciente de esto también.

 9
Author: Spencer Ruport,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-05-23 12:34:45

Funcionalmente no hay diferencia.

Sin embargo, hay una razón para no hacer esto. Los métodos más largos con varios puntos de salida a menudo son más difíciles de leer y analizar. Pero esa objeción tiene más que ver con declaraciones return que catch y finalmente blocks.

 4
Author: Ifeanyi Echeruo,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2009-01-16 08:37:48

En su ejemplo, de cualquier manera es equivalente, ni siquiera me sorprendería si el compilador generara el mismo código. Si ocurre una excepción en el bloque finally, tiene los mismos problemas, ya sea que coloque la instrucción return en el bloque o fuera de él.

La verdadera pregunta es estilísticamente qué es lo mejor. Me gusta escribir mis métodos para que solo haya una declaración de retorno, de esta manera es más fácil ver el flujo fuera del método, se deduce que también me gusta poner el retorno última declaración por lo que es fácil ver que es el final del método y esto lo que devuelve.

Creo que con la sentencia return tan bien colocada como la última sentencia, es menos probable que otras vengan y espolvoreen varias sentencias returns en otras partes del método.

 3
Author: BeWarned,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2009-01-16 01:08:07