Search code examples
loopslanguage-featuresstructured-programming

Is there any programming language which has a for-while loop?


This is what I mean by a for-while loop:

for (<init>; <update>) <body> while (<test>);

It roughly translates to:

<init>
<body>

while (<test>) {
    <update>
    <body>
}

This seems like a very common programming pattern. Yet, no language that I know of has such a control structure. Hence, a common workaround is to implement it as follows instead:

<init>

while (true) {
    <body>
    unless (<test>) break;
    <update>
}

While this works, it feels very clunky. In my humble opinion, having a conditional break in the middle of an infinite while loop goes against the spirit of structured programming.

Here's a motivational example for the need of for-while loops:

function swap(arr, i, j) {
    var tmp = arr[i];
    arr[i] = arr[j];
    arr[j] = tmp;
    return arr;
}

function heapify(heap, i) {
    var len = heap.length;

    for (var min = i; swap(heap, i, min), i = min) {
        var left  = 2 * i + 1;
        var right = 2 * (i + 1);

        if (left  < len && heap[left]  < heap[min]) min = left;
        if (right < len && heap[right] < heap[min]) min = right;
    } while (min !== i);

    return heap;
}

As you can see, the control is very easy to follow and the code is a lot cleaner than the workaround:

function swap(arr, i, j) {
    var tmp = arr[i];
    arr[i] = arr[j];
    arr[j] = tmp;
    return arr;
}

function heapify(heap, i) {
    var len = heap.length;
    var min = i;

    do (true) {
        var left  = 2 * i + 1;
        var right = 2 * (i + 1);

        if (left  < len && heap[left]  < heap[min]) min = left;
        if (right < len && heap[right] < heap[min]) min = right;

        if (min === i) break;
        swap(heap, i, min);
        i = min;
    }

    return heap;
}

Anyway, do you know of any programming language which has such a control structure? Lisp doesn't count because it's primarily functional and I'm looking for a primarily imperative programming language.


Solution

  • I realize that this isn't a completely satisfactory answer since c# does not have such a built-in control structure, but I had originally anticipated the syntax would be more concise so that it would have been nearly what you are looking for. (It turns out that c# will not do an implicit cast of the lambda expression to a boolean function, hence the explicit "garbage" surrounding the expression.)

    That aside, the following c# code demonstrates the alternate keyword choice I mentioned in the comments: do { <body> } while (<test>; <update>). This do-while-update syntax matches the pattern flow better than the for-while syntax you proposed. It's already questionable that any new construct would need a special place for <init> (as in for loops) unless you're concerned with scope of the construct variables, but in my experience no existing do-construct offers that anyway.

    var min = i; //<init>
    do {
        //<body>
        var left = 2 * i + 1;
        var right = 2 * (i + 1);
    
        if (left < len && heap[left] < heap[min])
            min = left;
        if (right < len && heap[right] < heap[min])
            min = right;
    } while ((min != 1) // <test>
        ? ((Func<bool>)(() => {
            swap(heap, i, min); i = min; //<update>
            return true; }))() : false);
    

    Note: The ternary conditional operator ensure that the <update> section is executed only when <test> is true.