How while loop wroks?

My previous question

name = 'Jesaa29 Roy'
size = len(name)
print(size)
i = 1
while i < size:
    if name[i].isspace():
        i += 1
        continue
    print(name[i], end='')
    i += 1

The point in this question was how continue is working here.

HERES NEW QUESTION

name = 'Jesaa29 Roy'
size = len(name)
print(size)
i = -1
while i < size:
    i = i +1
    if name[i].isspace():
        continue
    print(name[i], end='')

I thought it will be better to do “pre increment” rather than “post increment” like in my previous code
But I’m getting ‘string index out of range’

Edit: Ig I got the answer say if I’m right or wrong.
The condition will increase i till i is smaller than size
Size is length of Jessa29 Roy and is 11
Condition is while the i is smaller than size
so when i is 10 the condition is still met and i is increased to 11
The next come printing with index and since indexing starts with 0 the last index is 10
i is increased to 11 so it says ‘string index out of range’
while i < size - 1 should solve the problem

It would be good to also post a transcript of the output and error
messages. If nothing else it will point to the line where the error
occurred.

It can definitely be better to preincrement (or the equivalent for
whatever else you may be doing); it leaves the bottom of the loop body
free to do anything without affecting the control (in this case,
incrementing i).

You won’t see the above all that often because you start with i = -1,
which is itself out of range for the string. It isn’t wrong here, just a
little unintuitive.

Regarding the error, this is because your loop bound is now incorrect.

Previously, you were starting at 0 and counting while i < size. Now
you’re starting at -1, which means you want to count to i < size-1.
Because you increment after the test, when i == size-1 (which will
still pass your test) the increment takes you to i == size which is
then out of range for the string.

You’re iterating one time too many.

This kind of thing is why we often strive to use some version of the
code where i never takes on weird values like -1 (which is weird
only because string indices count from 0). By starting at -1 your
loop test now needs to test against size-1, which is more…
complicated than size. More complication means harder to read and
understand.

It is also why functions like range() exist: to make it easy to use
the values you want.

When you’re looking for this kind of error, it helps to call print()
with various interesting values. For example, if you’d updated the loop
like this:

 print("size =", size)
 i = -1
 print("before loop, i =", i)
 while i < size:
     print("top of loop: i =", i)
     i = i +1
     print("post increment: i =", i)
     if name[i].isspace():
         continue
     print(name[i], end='')

you’d see the extra value of i and therefore reason about how the
while-loop test expression is wrong.

This particular flavour of error is call an “off by one” error. We make
them all the time!

Cheers,
Cameron Simpson cs@cskk.id.au

3 Likes