Problem with while

Hello,

I have a problem with ‘while’ in the following code:

``````for i in range(1,5):
while(i<3):
print('hi')
print(str(i) + ' ' + 'in w')
i+=1
continue
print(i)
pass
print(i)
``````

The result is

``````hi
1 in w
hi
2 in w
hi
2 in w
4
``````

My question is why is there ‘2 in w’ twice and why is the last i printed equal to 4?
Thankyou.

Because you instructed Python to do so.

For loop emits integers 1, 2, 3, 4. While loop runs if integer value is less than three i.e. 1 and 2. While loop executes twice on 1 (1, 2) and once on 2.

Last i value in for-loop is 4 and therefore it printed at the end.

1 Like

If your confusion stems from the fact that the inner loop manipulates `i` and the outer loop’s next iteration doesn’t then “jump” to that future state, the while loop isn’t actually relevant. For example:

``````for i in range(5):
print(f"before modifying: {i}")
i = 0
print(f"after modifying: {i}")
``````

will print out:

``````before modifying: 0
after modifying: 0
before modifying: 1
after modifying: 0
before modifying: 2
after modifying: 0
before modifying: 3
after modifying: 0
before modifying: 4
after modifying: 0
``````

It doesn’t get stuck in an infinite loop at `1` forever as you might expect (because you set it to zero and then it gets incremented). The for loop’s iterator’s state isn’t stored in your local variable.

1 Like

There are multiple things to understand here.

1. When you nest loops, the complete inner loop happens again, each time that the outer loop runs.

2. Where the code says `for i in range(1,5):`, the `range(1,5)` part is not part of some special syntax for the `for` loop. `range` is not a keyword; it’s the name of a type - just like `int` and `str` and `list`. This code creates an object that represents some numbers, and then the `for` loop uses those numbers in sequence.

You can use a `for` loop with anything that is iterable - i.e., that represents multiple (zero or more) values that can be accessed in order, one at a time. For example, you can use a string (you get one character each time), or a text file that was opened for reading (you get one line of text from the file at a time), or a `dict` (you get each of its keys).

3. A `for` loop sets the value of its tracking variable, using the values from its element source. In this case, the source is `range(1, 5)`, which contains four values: `1`, `2`, `3` and `4`. So the `for` loop will run 4 times. It does not care about any change that is made to `i`, by any of the code inside the loop. It simply sets the value at the top of the loop, according to what it accesses from its source, in order, one at a time.

Only an abnormal exit (`break`, `return`, or raising an exception) or a modification to the element source (not possible here; `range` objects are immutable) can make the loop run a different number of times. At the beginning of the first time through the `for` loop, `i` is set to `1`. At the beginning of the second time through, it is set to `2`, regardless of anything that happened the first time through.

The first time through the `for` loop, `i` was set to `1`. So the `while` loop will check that `i < 3`, and print the messages for a value of `1`. It increments `i` to `2`, which is still less than 3, so it runs one more time. (The `print(i)` inside the `while` loop cannot happen, because `continue` skips it.) After the `while` loop, the `for` loop does `pass`, which has no effect (by definition). This is the first time that `2 in w` appears.

The second time through the `for` loop, `i` was set to `2`. So the `while` loop will check that `i < 3`, and print the messages for a value of `2`. It increments `i` to `3`, so it can’t run again. This is the second time that `2 in w` appears.

The third and fourth times through the `for` loop, the `i` value does not allow the `while` loop to be entered at all.

Because that is the value it has after the `for` loop has completed. The last time that the `for` loop runs, it sets `i` to `4`. The `while` loop does not run, because 4 is not less than 3, so there is no code that can change the value of `i` after that.

1 Like