2010-08-06 13 views
17

Algunas personas consideran las declaraciones de devolución múltiples como un mal estilo de programación. Si bien esto es cierto para los métodos más grandes, no estoy seguro de si es aceptable para los cortos. Pero hay otra pregunta: ¿Debería escribirse else explícitamente, si hay una declaración de devolución en el if anterior?¿Vuelve de un método con "else" implícito o explícito o con una sola declaración de "devolución"?

implícito else:

private String resolveViewName(Viewable viewable) { 
    if(viewable.isTemplateNameAbsolute()) 
     return viewable.getTemplateName(); 
    return uriInfo.getMatchedResources().get(0).getClass().toString(); 
} 

explícita else:

private String resolveViewName(Viewable viewable) { 
    if(viewable.isTemplateNameAbsolute()) 
     return viewable.getTemplateName(); 
    else 
     return uriInfo.getMatchedResources().get(0).getClass().toString(); 
} 

Técnicamente else no es necesario aquí, pero hacen el sentido más obvio.

Y tal vez el enfoque más limpio con una sola declaración:

private String resolveViewName(Viewable viewable) { 
    String templateName; 
    if(viewable.isTemplateNameAbsolute()) 
     templateName = viewable.getTemplateName(); 
    else 
     templateName = uriInfo.getMatchedResources().get(0).getClass().toString(); 
    return templateName; 
} 

Cuál prefiere? ¿Otras sugerencias?

+3

Una instrucción de retorno sola no suele ser lo necesite para un buen método corto como este ya que tener dos es igual de fácil de leer, y por lo general, a m e al menos, más lógico en la mayoría de las situaciones. – Nobody

+7

Si bien el uso de else es meramente un gusto por la materia, creo que esta cadena de monstruos 'uriInfo.getMatchedResources(). Get (0) .getClass(). ToString()' es más preocupante. Esto solo pide Excepciones en algún punto que probablemente debería evitarse con unos pocos controles adicionales. – x4u

+0

"Algunas personas consideran las declaraciones de devolución múltiples como un mal estilo de programación". ver http: // stackoverflow.com/questions/36707/should-a-function-have-only-one-return-statement – Raedwald

Respuesta

22

Otra sugerencia obvia: use el operador condicional.

private String resolveViewName(Viewable viewable) { 
    return viewable.isTemplateNameAbsolute() 
     ? viewable.getTemplateName() 
     : uriInfo.getMatchedResources().get(0).getClass().toString(); 
} 

Para los casos donde esto no es viable, casi con seguridad soy inconsistente. No me preocuparía demasiado por eso, para ser sincero, no es el tipo de cosa en la que la capacidad de lectura se ve significativamente afectada de ninguna manera, y es poco probable que presente errores.

(Por otra parte, me habría sugerir el uso de aparatos ortopédicos para todos los bloques if, los estados, incluso individuales.)

+0

Voy a tener que estar de acuerdo con usar siempre llaves (cambié mi respuesta para reflejar eso), aunque generalmente dejo que Eclipse maneje eso para yo con autoformato + guardar acciones. –

+0

+1 - aunque creo que tienes una paren cercana adicional allí. – Carl

+0

@Carl: corregido, gracias. –

4

por lo general prefiero la primera opción, ya que es la más corta.

Y creo que cualquier programador decente debería darse cuenta de cómo funciona sin tener que escribir el resto o usar una sola declaración al final.

además de que hay casos en los métodos de largo, donde puede que tenga que hacer algo como

if(!isValid(input)) { return null; }// or 0, or false, or whatever 
// a lot of code here working with input 

Me parece que es aún más claro hecho así para este tipo de métodos.

3

Depende de la intención. Si la primera devolución es un rescate rápido, entonces me iría sin el else; si OTOH es más como un escenario de "devolver esto o aquello", entonces usaría else. Además, prefiero una declaración de devolución anticipada sobre declaraciones if anidadas interminablemente o variables que existen con el único propósito de recordar un valor devuelto. Si tu lógica fuera un poco compleja, o tal como es ahora, consideraría poner las dos formas de generar el valor de retorno en funciones dedicadas, y usar un if/else para llamar.

0

Claro, la gente tiene mucho que decir sobre el estilo de programación, pero no se preocupe por algo relativamente trivial para el propósito de su programa.

Personalmente, me gusta ir sin el resto. Si alguien está revisando tu código, hay muchas posibilidades de que no se confunda demasiado sin el otro.

1

Prefiero el primero.

O ... puede usar if return else return para bifurcaciones igualmente importantes, y if return return para casos especiales.

Cuando tiene aserciones (if p==null return null), entonces la primera es la más clara con diferencia. Si tiene opciones igualmente ponderadas ... Me parece bien utilizar el else explícito.

0

Prefiero la segunda opción porque para mí es la más rápida de leer.

Evitaría la tercera opción porque no agrega claridad o eficiencia.

La primera opción también está bien, pero al menos pondría una línea en blanco entre el primer bit (el retorno si y su sangrado) y la segunda declaración de retorno.

Al final, se trata de preferencias personales (como tantas cosas en el estilo de programación).

6

prefiero el enfoque más limpio con retorno único. Para mí, el código es legible, fácil de mantener y no confuso. Mañana si necesita agregar algunas líneas al bloque if o else es fácil.

1.) el código nunca debe ser inteligente.

1

Es una cuestión de preferencia personal. Literalmente he pasado por las fases de hacer las 4 opciones (incluida la publicada por Jon Skeet). Ninguna de ellas está mal, y nunca he tenido inconvenientes. un resultado de usar cualquiera de ellos.

3

Prefiero retornos múltiples en una estructura if-else cuando el tamaño de ambas declaraciones es casi igual, el código se ve más equilibrado de esa manera. Para expresiones cortas, uso el operador ternario. Si el código para una prueba es mucho más corto o es un caso excepcional, podría usar una sola si el resto del código permanece en el cuerpo del método.

Intento evitar la modificación de variables tanto como sea posible, porque creo que hace que el código sea mucho más difícil de seguir que las salidas múltiples de un método.

+0

+1 para la diferencia entre rutas de código igualmente válidas y condiciones de guarda excepcionales. – ILMTitan

0

Considerando múltiples declaraciones de devolución "mal estilo" es una falacia larga, largamente desacreditada. Pueden hacer que el código sea mucho más claro y más fácil de mantener que las variables explícitas de valor de retorno. Especialmente en métodos más grandes.

En su ejemplo, consideraría que la segunda opción es la más limpia porque la estructura simétrica del código refleja su semántica, es más corta y evita la variable innecesaria.

1

El material sobre una sola declaración de devolución data de la década de 1970 cuando Dijkstra y Wirth estaban clasificando la programación estructurada. Lo aplicaron con gran éxito para controlar las estructuras, que ahora se han establecido de acuerdo con su prescripción de una entrada y una salida. Fortran solía tener múltiples entradas a una subrutina (o posiblemente a una función, perdón, unos 35 años desde que escribí alguna), y esta es una característica que nunca me he perdido, de hecho, no creo haberla usado nunca.

Nunca me he encontrado con esta 'regla' como se aplica a métodos fuera del mundo académico, y realmente no puedo ver el punto. Básicamente tienes que ofuscar tu código considerablemente para obedecer la regla, con variables adicionales y demás, y no hay forma de que puedas convencerme de que es una buena idea. Curiosamente, si lo escribe de forma natural según su primera opción, el compilador normalmente genera el código de acuerdo con la regla de todos modos ...para que pueda argumentar que la regla es obedecida: simplemente no por usted ;-)

2

Mantenga la jerga coherente y legible para el programador de menor denominación común que podría tener que volver a visitar el código en el futuro.

Son solo unas pocas letras extra para escribir el resto, y no hace diferencia a nada excepto a la legibilidad.

6

El dogma del "punto de salida único" viene de los días de la Programación Estructurada.

En su día, la programación estructurada era BUENA COSA, especialmente como una alternativa al código de espagueti montado en GOTO que prevalecía en los códigos Fortran y Cobol de la década de 1960 y 1970. Pero con la popularidad de idiomas como Pascal, C y demás con su gama más rica de estructuras de control, la Programación Estructurada se ha asimilado a la programación convencional, y ciertos aspectos dogmáticos han caído en desuso. En particular, la mayoría de los desarrolladores se alegran de tener múltiples salidas de un bucle o método ... siempre que haga que el código sea más fácil de entender.

Mi sensación personal es que en este caso particular, la simetría de la segunda alternativa hace que sea más fácil de entender, pero la primera alternativa es casi tan legible. La última alternativa me parece innecesariamente prolija, y la menos legible.

Pero @Jon Skeet señaló que hay un problema de estilo mucho más significativo con su código; es decir, la ausencia de {} bloques alrededor de las instrucciones 'then' y 'else'. Para mí el código realmente debe escribirse así:

private String resolveViewName(Viewable viewable) { 
    if (viewable.isTemplateNameAbsolute()) { 
     return viewable.getTemplateName(); 
    } else { 
     return uriInfo.getMatchedResources().get(0).getClass().toString(); 
    } 
} 

Esto no solo es una cuestión de hermosura código. En realidad, hay un punto serio para usar siempre bloques. Considere esto:

String result = "Hello" 
if (i < 10) 
    result = "Goodbye"; 
    if (j > 10) 
     result = "Hello again"; 

A primera vista, parece que resultado será "Hola de nuevo" si i es inferior a 10 y j es mayor de 10. De hecho, esto es una mala interpretación - hemos sido engañados por indentación incorrecta. Pero si el código se hubiera escrito con { } alrededor de las partes entonces, estaría claro que la sangría era incorrecta; p.ej.

String result = "Hello" 
if (i < 10) { 
    result = "Goodbye"; 
    } 
    if (j > 10) { 
     result = "Hello again"; 
    } 

Como se ve, la primera } se destaca como un pulgar dolorido y nos dice que no confía en la muesca como una señal visual a lo que significa el código.

1

Has solicitado que otras sugerencias, ¿qué hay de

Uso afirma o RuntimeExceptions

private String resolveViewName(Viewable viewable) { 
    if(viewable.isTemplateNameAbsolute()) 
     return viewable.getTemplateName(); 
    else 
     return uriInfo.getMatchedResources().get(0).getClass().toString(); 
    throw new RuntimeException ("Unreachable Code") ; 
    } 

Usar la palabra clave final

private String resolveViewName(Viewable viewable) { 
final String templateName; 
if(viewable.isTemplateNameAbsolute()) 
    templateName = viewable.getTemplateName(); 
else 
    templateName = uriInfo.getMatchedResources().get(0).getClass().toString(); 
return templateName; 
} 
+0

'final' es una buena adición. – deamon

+0

¿Por qué agregaste esta RuntimeException? – DerMike

+0

@DerMike Creo que debido a las devoluciones anteriores, la RuntimeException es inalcanzable. Si se lanza, sabré que estaba equivocado. – emory

Cuestiones relacionadas