Question

for example...

if ( /* Condition */ ) {

    if ( /* Condition */ ) {

        if ( /* Condition */ ) {

          // Superb!

        } else {

          // Error 3

        }

    } else {

      // Error 2

    }

} else {

  // Error 1

}

Do you know how to avoid this? Thank you!

Was it helpful?

Solution

If this is a library function, throw may be the appropriate action.

if (!condition1) {
    throw "Condition 1 failed.";
}

if (!condition2) {
    throw "Condition 2 failed.";
}

if (!condition3) {
    throw "Condition 3 failed.";
}

// Superb!

Other acceptable actions might be:

  • Returning 0, null, or undefined.
  • Displaying an error to the user and returning.

You will have to determine which failure action is right for your use case.

OTHER TIPS

It looks like you have 3 conditions to check and 4 actions (3 different errors + 1 success). Unfortunately in the general case it's going to require 3 conditional checks and 4 actions. I think the code can be cleaned up a bit by using the following structure though

if (! /* condition 1 */ ) {
  // Error 1
} else if (! /* condition 2 */ ) { 
  // Error 2
} else if (! /* condition 3 */ ) { 
  // Error 3
} else {
  // superb
}

Well you can use exceptions, or breaks within a block, or multiple functions. Often this requires inverting your conditions to get the code ordered the right way.

do {
    if (! /* Condition 1 */ ) {
        // Error 1
        break;
    }

    if (! /* Condition 2 */ ) {
        // Error 2
        break;
    }

    if (! /* Condition 3 */ ) {
        // Error 3
        break;
    }

    // Superb!
} while (false);

The do-while(false) loop is a way of making a block that you can break out of in languages that will not tolerate an anonymous block. It could just as easily be a function and use returns, or a try-catch with exceptions.

Would you prefer this?

if ( /* Condition 1*/ && /* Condition 2*/ && /* Condition 3 */) {
  // Superb!
}
else if (! /* Condition 1*/){
  // Error 1
}
else if (! /* Condition 2*/){
  // Error 2
}
else if (! /* Condition 3*/){
  // Error 3
}
if ( ! /* Condition */ ) {
Error 1
throw someSortOfException
}

if (! condition 2){
Error 2
throw someSortOfOtherException
}

if (! condition 3){
Error 3
throw another Exception
}

// Success!

Depending on the situation, your code may be prefered. You'll probably want to catch those exceptions somewhere for example.

if (!condition1)
    // Error 1 (and exit scope if necessary)

if (!condition2)
    // Error 2 (and exit scope if necessary)

if (!condition3)
    // Error 3 (and exit scope if necessary)

// Superb!

Yes; you can compose together your if statements into a single compound statement using the AND operator, and handle the error conditions in a single block. Depending on your error handling needs, though, you may need to again have multiple ifs to make sure you're properly handling the error (it depends on your error handling resolution, really).

To wit:

if (CondA && CondB && CondC)
   {
   // Execute success
   }
else
   {
   if (!CondA)
      // Do error A
   else if (!CondB)
      // Do error B
   else if (!CondC)
     // Do error C
   }
}

There are a few ways, the simplest is to simply bust out some functions and abstract out the different layers (this should be done anyway if you find yourself going deep.)

if ( /* Condition */ ) {
    value = aFunctionSaysWhat();
} else {
  // value = Error 1
}

....
value aFunctionSaysWhat(){
    if ( /* Condition */ ) {
         return aSecondFunctionHere();
    } else {
      // return Error 2
    }
}

The basic premise is that a function should live on one layer of abstraction if possible, and do one thing.

The next possibility is to flatten it all out, this is superior to your initial nested method, but basically has similar complexity. It could be much cleaner than the functional approach if you only have a few options and you don't plan on adding more.

if(ErrorCondition1){
   //Error 1
}else if(ErrorCondition2){
   //Error 2
}else if(ErrorCondition3){
   //Error 3
}else{
   //Superb
}

Finally, you can store a hash or map with the desired answers and remove the if completely, the ability to implement this relies on your ability to hash some result:

Results = {'Result1':'Error1', 'Result2':'Error2', 'Result3':'Error3', 'Success':'Superb'}

return Results[ConditionHash(Condition)];
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top