开发者

Does the construct do .. while(false) contribute to better control flow?

开发者 https://www.devze.com 2023-01-28 07:05 出处:网络
I\'ve recently come across this code: do { if ( ! checkSomething() ) break; // some code if ( ! checkSomeOtherThing() )

I've recently come across this code:

do {
    if ( ! checkSomething() )
        break;

    // some code

    if ( ! checkSomeOtherThing() )
        break;

    // some other code
} while(false);

// some final code
开发者_如何转开发

The programmer that wrote it, wrote a comment along the lines of "cleaner control flow".

In my opinion, the original code could look better if its refactored into something else. But is there any truth in this statement ? Is this construct any good ?


I find this much easier to read, and it produces an identical result:

if ( checkSomething() )
{
    // some code
    if ( checkSomeOtherThing() )
    {
        // some other code
    }
}
// some final code

I think do ... while is normally hard to follow, but using it for something other than a loop is misleading at best.


This is equivalent to a goto.

In such situations, it is better to use a goto than to use an ugly hack.

Changing it to use a goto makes it much more readable:

if (!checkSomething())
    goto Done;

// some code

if (!checkSomeOtherThing())
    goto Done;

// some other code
Done: //some final code


If you don't mind loops containing several break statements, then the only problem here is that C (for obvious reasons) doesn't let you break out of a bare block, hence the "non-loop" which some unsuspecting future maintainer could mistake for a real loop.

The considerations, I think, are:

  • if there are only two break points, what's so bad about two if statements?
  • if there are more than two break points then the indentation with if statements could get unpleasant, and this saves that, but then again is the function doing too much? And even if not, would it be better just to use goto and avoid the weirdness of a loop that doesn't loop?

Since you tag this language-agnostic, I used to use a macroised assembly language, with a block ... endblock that you could break out of. This lead to reasonably nice code for checking necessary conditions, such as:

block
    breakif str1 == null
    breakif str2 == null
    get some combined property of str1 and str2
    breakif some other condition that stops us getting on with it
    get on with it
endblock

Actually, it wasn't breakif str1 == null, it was breakifeq.p str1, null, or something like that, but I forget exactly what.


I've seen the do-while form adopted as a standard to which coders conformed. The advantage is that it communicates, and implements, that the loop will always be executed at least once. This helps isolate, with consistency, the situations where something different occurs, i.e. where the code in the loop is not executed.

This standard was adopted because the Warnier-Orr technique was being applied.

0

精彩评论

暂无评论...
验证码 换一张
取 消