Pregunta

Tengo curiosidad por ver alguna alternativa (s) a las declaraciones regulares si

if(x)
     do a;
if(y)
     do b;
if(z)
    do c;

para que veas todas si las declaraciones están separadas y no hay otra condición. Tenga en cuenta que X Y Z son condiciones totalmente independientes, por lo que el interruptor no encajaría.

¿Fue útil?

Solución

Uno " verdaderamente orientado a objetos " La respuesta sería definir una interfaz para " Regla " (con los métodos de condición () y acción ()), cree 3 implementaciones, rellénelas en una colección y luego itérelas genéricamente como en:

List<Rule> rules = .... ; // your 3 rules initialized here somehow
for(Rule r : rules) {
  if(r.condition()) {
    r.action();
  }
}

Esto tiene mucho más sentido si tiene 300 reglas / condiciones en lugar de solo 3.

En Java8, es posible que desee hacer esto en su lugar, si las reglas hacen un uso intensivo de la CPU:

rules.parallelStream().filter(Rule::condition).forEach(Rule::action);

Otros consejos

La respuesta corta es sí.

Hay algunas veces que puedes evitar usarlos para la evitación condicional y la bifurcación. Y tienen momentos de adecuación.

  1. Polimorfismo, cuando el comportamiento depende de los valores iniciales
  2. Asignación de referencia, cuando conoce los posibles valores iniciales y tienen una correlación de 1 a 1 con los valores de retorno. Las listas son mejores que las matrices para esto, pero ...
       

    // Example:  
    if (a==1) { b=2;  }  
    if (a==2) { b=17; }  
    
    // Becomes  
    int fx(2);  // our array of answers  
    fx[0] = 2;   
    fx[1] = 17;  
    b = fx[ a - 1 ];
    
  3. Ramificación a la que se hace referencia, cuando conoce los posibles valores iniciales y tienen una correlación de 1 a 1 con la función / rama a usar. (ejemplo no Java)

    // Example:
    if (a==1) { doSomething1();  }  
    if (a==2) { doSomething2(); }  
    
    // Becomes
    function * fx(2);  // our array or better still, list of functions  
    fx[0] = &doSomething1;   
    fx[1] = &doSomething2;  
    `fx[ a - 1 ](); `
    
  4. Asignación booleana directa.

    Odiamos:

    if (thisCondition == true) {  
      b = true;  
    } else {  
      b = false;  
    }
    

    Debería ser:

      

    b = thisCondition;

Las alternativas a if-else en Java son la declaración de cambio y ternario condicional (?: ), ninguno de los cuales hace exactamente lo que está preguntando (maneja solo un si sin else ). El código que publicaste es la mejor manera de hacerlo, en mi opinión.

Usa el polimorfismo.

interface SomethingDoer {
    public void doSomething();
}

class ADoer implements SomethingDoer { ... }
class BDoer implements SomethingDoer { ... }
class CDoer implements SomethingDoer { ... }

public class Main {
     public static void main (String[] args) {
          SomethingDoer doer = new SomethingDoerFactory(args).getDoer();
          doer.doSomething();
     }
}

El if no se elimina por completo, pero se mueve a SomethingDoerFactory. Esta solución no es aplicable en todos los casos, pero en algunos de ellos es una muy buena alternativa a múltiples ifs.

Aquí hay una bonita charla al respecto:
http://misko.hevery.com / 2008/12/08 / clean-code-talks-inheritance-polymorphism-testing /

esta es la solución más simple, legible pero eficaz . Me sorprendería ver alternativas efectivas aquí.

EDIT

puede intentar aplicar método de extracción varias veces:

doAIfX();
doBIfY();
doCifZ();

donde los métodos se definen por:

void doAIfX() {
    if (!X) {
        return;
    }

    // do 'a'
}

realmente depende de lo que sean x, y, z y a, b, c. A veces, si las declaraciones son más adecuadas. A veces el polimorfismo es más adecuado.

Necesitará tener estas declaraciones if en algún lugar.

Se pueden refactorizar en otros métodos para mantener limpio el método actual, como han sugerido otros. Si necesita reutilizar este mismo conjunto de sentencias if en varios lugares, podría utilizar el Patrón de decorador .

Parece un caso perfecto para usar cierre . Pero para eso necesitas groovy o algo similar.

¿Qué tal ... myAnimator (thing, pos, speed | computeSpeed ??())

si speed === undefined entonces computeSpeed ??... creo.

Realmente depende del contexto ... pero sí, if-else es solo una de las declaraciones de flujo de control en java: https://docs.oracle.com/javase/tutorial/java/ nutsandbolts / flow.html

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top