Looping [was Re: Python and the need for speed]

Steve D'Aprano steve+python at pearwood.info
Sat Apr 15 22:51:46 EDT 2017


On Sat, 15 Apr 2017 10:17 pm, bartc wrote:

> On 15/04/2017 03:35, Rick Johnson wrote:
>> On Wednesday, April 12, 2017 at 8:44:30 AM UTC-5, bart... at gmail.com
>> wrote:
> 
>> At a minimum, every language should offer
>> the following four loop-forms (using Python semantics):
>>
>>     while CONDITION:
>>         doSomething()
>>
>>     for VALUE in COLLECTION:
>>         doSomething(value)
>>
>>     loop(N):
>>         doSomething()
>>
>>     loop(N) as i:
>>        doSomething(i)


What an extravagant, unnecessary waste of syntax. The last two just
duplicate the functionality of the second. AND Rick has forgotten about the
do...while form that executes the block at least once.

I've used, and to be honest really enjoyed using, a language with multiple
loop syntax like this. I can see some advantage in offering specialist
English-like loops in a programming language for non-programmers and
amateurs. But having a plethora of forms for what is essentially the same
thing is not so helpful for more skilled programmers who are more
comfortable with composing code rather than memorising fixed statements.


    repeat forever:
        ...


is no more expressive than

    while True:
        ...


since they're both just the same thing. You can mechanically and trivially
translate one to the other with no intelligence needed. So it becomes a
mere matter of personal taste as to which you prefer.


> Yes, I'm constantly surprised at this, as such syntax has a very low
> cost (in my last compiler, supporting 'while' for example only added 30
> lines to the project).

That's the advantage of writing your own private language and having no
users except for yourself. You get to cut corners. Python has tens of
thousands of users, and doesn't have that luxury.

For language developers with responsibilities to users, the job doesn't stop
at just implementing the feature in the language. It also needs to be
tested and documented.

As a general rule of thumb, every line of production code should expect to
add at least ten lines of test code (unit tests, regression tests,
integration tests, functional tests, doc tests, etc). So for your "30
lines" feature, that adds 300 lines of tests, and probably another page or
two of documentation:

- describing the various syntax forms;
- explaining how they differ;
- tutorials for beginners showing each form;

plus the on-going burden for every single user of the language, for ever, in
having to decide which form they need to use in any specific circumstance.

The more choices you offer, the harder that decision becomes:

- numeric Pascal or C-style loop
- foreach style loop
- repeat while condition (test at start)
- repeat until condition (test at start)
- do ... while condition (test at end)
- do ... until condition (test at end)
- repeat forever


I don't remember the language, but I remember seeing one generalisation of
the repeat/do loop that puts the test in the middle, rather than at the
start or end of the loop. If I remember it was something like:

DO
    setup code  # executed once only
REPEAT
    loop body  # before the test
WHILE condition  # test
    loop body  # after the test

thus combining both the 

    repeat while condition:
        ...

and

    do:
        ...
    until condition


styles of looping in one handy syntax.


> Of course, it's possible to overdo it; if you look at Lisp, you'll lose
> yourself in the myriad looping options.

"Myriad"? As I understand it, Lisp offers just *one* more loop construct
than the number you agree is the "minimum" needed: five.

loop
loop for
do
dotimes
dolist


https://www.tutorialspoint.com/lisp/lisp_loops.htm



> But very common requirements are endless loops, and repeat N times
> without needing an explicit counter. 

If by "very common" you mean "occasionally", I agree.


> The former /can/ be easily written 
> as:
> 
>      while 1:
>          body
> 
> but it's more psychological; I don't want to use an idiom to denote an
> endless loop, I want to be able to express it directly!

"Express it directly" is an idiom, and "while True" is just as direct
as "repeat forever".


> Python's byte-code does at least optimise out the check that '1' is
> true, but that's not what the reader sees, which is 'loop while 1 is
> true'. And one day it will be:
> 
>      while l:
>          body
> 
> that can be mistaken for that common idiom.

The problem there is not the loop, but the foolish use of lowercase l as a
variable name. It is simply poor programming practice to use easily
confused names, and the problem here is not the use of `while`.

No more than it is the use of `while` that makes this code bad:

while O000IlI1III11IIII1IllOO:
    something()
    O000IlI1III11I1II1IllOO = False
    print(O00OIlI1III11IIII1IllOO)


Given:

    mylist.append(l)
    x += l
    if l: ...

do you also conclude that the problem lies with append, += and `if` ?

 

-- 
Steve
“Cheer up,” they said, “things could be worse.” So I cheered up, and sure
enough, things got worse.



More information about the Python-list mailing list