Domanda

Long winding condizioni if dovrebbe essere evitato se possibile, eppure a volte siamo tutti finiscono per scriverli. Anche se si tratta di una condizione molto semplice, le dichiarazioni coinvolti sono a volte semplicemente molto prolisso, in modo che l'intera condizione finisce per essere molto lungo. Qual è il modo più leggibile per formattare quelli?

if (FoobarBaz::quxQuux(corge, grault) || !garply(waldo) || fred(plugh) !== xyzzy) {
    thud();
}

o

if (
    FoobarBaz::quxQuux(corge, grault)
 || !garply(waldo)
 || fred(plugh) !== xyzzy
) {
    thud();
}

o

if (FoobarBaz::quxQuux(corge, grault)
    || !garply(waldo)
    || fred(plugh) !== xyzzy) {
    thud();
}

o

thudable = FoobarBaz::quxQuux(corge, grault);
thudable ||= !garply(waldo);
thudable ||= fred(plugh) !== xyzzy;

if (thudable) {
    thud();
}

o qualsiasi altre preferenze?

È stato utile?

Soluzione

Spesso, un lungo se la condizione è il segno di codice che deve refactoring, ma a volte non si può evitare. In questi casi, io preferisco la prima:

if (bar || baz || quux) { ... }

Perché tu sei in grado di dire che cosa sta succedendo con una linea. Tuttavia, mi piacerebbe molto meglio fare qualcosa di simile, quando possibile:

function foo() {
  return bar || baz || quux;
}

if (foo()) { ... }

Altri suggerimenti

I come tenere gli operatori al fine di indicare seguito:

if (the_function_being_called() != RETURNCODE_SUCCESS &&
    the_possibly_useful_recovery_strategy() == RETURNCODE_EPICFAIL &&
    this_user_has_elected_to_recieve_error_reports)
{
    report_error();
}

Sono un grande fan di nomi di variabili significative:

const bool isInAStrangeCondition =
    FoobarBaz::quxQuux(corge, grault) ||
    !garply(waldo) ||
    fred(plugh) !== xyzzy;

if (isInAStrangeCondition) {
    thud();
}

O refactoring come una funzione, come detto sopra.

I rompere le sottoespressioni Messier, o tutti loro, come variabili bool. Poi la logica booleana di livello superiore del 'se' dichiarazione può essere chiaro. Nel tipo di lavoro che faccio, non è sempre diverse cose ORed o ANDed.

bool goodblah = some_mess < whatever;
bool frobnacious = messy_crud != junky_expression;
bool yetanother = long_winded_condition;

if (goodblah || (frobnacious && yetanother))   {
    ...
}

Ciò è particolarmente utile in un debugger, dove posso guardare tutti i Caccio prima di eseguire il 'se'.

I tendono ad allineare gli operatori all'inizio di nuove linee così mi ricordo come sto combinando termini (sia a lungo logica e lungo l'aritmetica). In questo modo:

if (first_attempt(data) == SUCCESS
    || (reusable(data) && second_attempt(data) == SUCCESS)
    || (still_reusable(data) && third_attempt(data) == SUCCESS))
  return SUCCESS;

Questo funziona solo se mi trattino da 2-spazi o set impostato il mio ambiente di predicati più righe di rientro più, altrimenti sarebbe difficile dire dove finisce predicato e codice utile comincia.

Sono un fan dei seguenti:

if (really_long_expression && another_really_really_long_expression && 
            another_very_long_expression_OMG_id_it_long){
    bugs();
}

In questo modo appare ancora come un se espressione e non un caso espressione down to-pezzi rotti. Il rientro aiuta a dimostrare che si tratta di una continuazione della linea precedente.

È anche possibile rientro fino a quando la parentesi di apertura si trova alla fine della riga precedente in modo che sia alla fine del se espressione come si suppone che sia.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
scroll top