While Loops¶
In these notes you will learn:
- How to create an infinite loop using a while-loop.
- How to write and trace while-loops that perform simple task such as incrementing variables.
Introduction¶
Suppose you want to print the numbers from 1 to 1000 on the screen. You could do it like this:
println(1);
println(2);
println(3);
// ...
println(1000);
Writing 1000 lines of code is pretty tedious. It’s easy to make a mistake, and it’s also inflexible — what if you wanted to print the numbers from 500 to 5000 instead?
A much better solution is to use a while-loop. A while-loop repeats a block of code zero or more times.
Infinite Loops¶
The simplest kind of loop is a loop that never stops, i.e. an infinite loop. We can use a while-loop to create an infinite loop like this:
while (true) { // infinite loop
println("Hello!");
}
It prints Hello!
forever:
Hello!
Hello!
Hello!
Hello!
...
Loops that Stop¶
Suppose we want to print the numbers 1 to 10 on the screen using a while-
loop. The standard technique for doing this is to use a variable, say i
,
to keep track of how many times the block of code in the while-loop has been
executed. For example:
int i = 1;
while (true) { // infinite loop
println(i);
++i; // adds 1 to i (same as i += 1)
}
println("done");
This loop prints this:
1
2
3
4
...
This illustrates the important idea of incrementing a variable inside a loop, but it is still an infinite loop that never stops.
How do we get the loop to stop? The condition at the top of the loop decides
if the code block underneath it is executed or skipped. So far our while-loop
condition has always been true
:
while (true) { // condition for this loop is "true": always executes
// ... the code block underneath
}
We can use any boolean expression (i.e. an expression that evaluates
to either true
or false
) as the condition for a while-loop. For
example:
int i = 1;
while (i <= 10) {
println(i);
++i;
}
println("done");
Now the while-loop condition is i <= 10
, which means that the block of
code under the while-loop will only be executed when i <= 10
is true
.
If i <= 10
is false
, then the loop stops and jumps down to the first
statement after the loop (i.e. println("done")
).
And that’s really all there is to while-loops: the condition at the top
decides whether or not to execute the block of code underneath. When the
condition is false
the loop is over, i.e. it is terminated.
Tracing a while-loop¶
Look again at this loop:
int i = 1;
while (i <= 10) {
println(i);
++i;
}
println("done");
The best way to understand loops is to “play computer” and trace the code by
hand, keeping track of the value of i
as you go. Tracing it by hand, you
do something like this:
i
is initially set to 1.- The first time the loop condition is checked,
i
is 1, and soi <= 10
istrue
. Thusprintln(i)
is called, causing 1 to be printed. Then 1 is added toi
, making it equal to 2. - After the code block is executed, the loop condition is checked again. Since
i
is 2,i <= 10
istrue
, and so 2 is printed andi
is incremented to 3. - After the code block is executed, the loop condition is checked again. Since
i
is 3,i <= 10
istrue
, and so 3 is printed andi
is incremented to 3.
You can see how the pattern continues. Eventually, i
becomes 10. The loop
condition i <= 10
is true
, and so 10 is printed and i
is
incremented to 11.
The next time the loop condition is checked, i <= 10
is false
because
i
is 11. A false
loop condition makes the loop skip its body block and
jump directly whatever statements follow the loop.
Tracing loops is a valuable skill that you should practice. Loops in real programs can get tricky, and tracing them by hand is often the best way to understand what it does.
Adding Objects to an ArrayList¶
In previous notes we saw code like this for adding
a lot of bouncing ball objects to an ArrayList
:
// ...
ArrayList<BouncingBall> ballList; // initially null
void setup() {
size(500, 500);
// create the initially empty ArrayList of BouncingBall objects
ballList = new ArrayList<BouncingBall>();
// add 10 bouncing ball's
ballList.add(randomBouncingBall());
ballList.add(randomBouncingBall());
ballList.add(randomBouncingBall());
ballList.add(randomBouncingBall());
ballList.add(randomBouncingBall());
ballList.add(randomBouncingBall());
ballList.add(randomBouncingBall());
ballList.add(randomBouncingBall());
ballList.add(randomBouncingBall());
ballList.add(randomBouncingBall());
}
void draw() {
background(255);
// render and update all the balls
for(BouncingBall b : ballList) {
b.render();
b.update();
}
}
A better approach is to use a while-loop:
// ...
int NUM_BALLS = 10;
void setup() {
// ...
int i = 0;
while (i < NUM_BALLS) {
ballList.add(randomBouncingBall());
i += 1;
}
}
// ...
The while-loop not only greatly shortens the code, but also makes it trivial
to change the number of balls by setting NUM_BALLS
.
Questions¶
What does each of the following code fragments print?
int a = 5; // fragment 1 while (a <= 10) { println(a); ++a; } int a = 5; // fragment 2 while (a < 10) { println(a); ++a; int a = 5; // fragment 3 while (a <= 10) { ++a; println(a); } int a = 5; // fragment 4 while (a < 10) { ++a; println(a); } int a = 5; // fragment 5 while (a != 10) { println(a); ++a; } int a = 5; // fragment 6 while (a != 10) { ++a; println(a); ++a; }
What does each of the following code fragments print?
int k = 5; // fragment 1 while (k > 1) { println(k); --k; } int k = -1; // fragment 2 while (k > -5) { println(k); --k; } int k = -1; // fragment 3 while (k > -5) { --k; println(k); }
What does each of the following code fragments print?
int b = 0; // fragment 1 while (b < 10) { println(b); b += 2; } int b = 0; // fragment 2 while (b <= 10) { println(b); b += 2; } int b = -10; // fragment 3 while (b < 0) { println(b); b += 3; } int b = 10; // fragment 4 while (b >= 0) { println(b); b -= 2; } int b = 0; // fragment 5 while (b < 10) { println(b); b *= 2; } int b = 1; // fragment 6 while (b < 10) { println(b); b *= 2; }
Write a file loop that prints the following sequences of numbers. There should be exactly one
println
statement in the body of your while loop that prints one number of the sequence on each iteration.- 1, 2, 3, 4, 5
- 5, 4, 3, 2, 1
- -1, -2, -3, -4, -5
- -5, -4, -2, -1
- 1, 3, 5, 7, 9
- 9, 7, 5, 3, 1
- -5, 0, 5, 10, 15
- 1, 1, 2, 2, 3, 3, 4, 4 (remember that there should be exactly one
println
statement in the body of your while-loop that prints exactly one number of the sequence) - 1, -1, 2, -2, 3, -3, 4, -4 (remember that there should be exactly one
println
statement in the body of your while-loop that prints exactly one number of the sequence) - -1, 1, -2, 2, -3, 3, -4, 4 (remember that there should be exactly one
println
statement in the body of your while-loop that prints exactly one number of the sequence)
Explain why the following is not an infinite loop:
int n = 1; while (n > 0) { println("loop"); ++n; }
Code¶
class Sprite {
float x;
float y;
float dx;
float dy;
void update() {
x += dx;
y += dy;
}
}
class BouncingBall extends Sprite {
float diam;
color fillColor;
void render() {
pushMatrix();
noStroke();
fill(fillColor);
ellipse(x, y, diam, diam);
popMatrix();
}
void update() {
x += dx;
y += dy;
// hit top?
if (y - diam / 2 < 0) {
y = diam / 2;
dy = -dy;
}
// hit bottom?
if (y + diam / 2 > height) {
y = height - diam / 2;
dy = -dy;
}
// hit left?
if (x - diam / 2 < 0) {
x = diam / 2;
dx = -dx;
}
// hit right?
if (x + diam / 2 > width) {
x = width - diam / 2;
dx = -dx;
}
}
}
BouncingBall randomBouncingBall() {
BouncingBall ball = new BouncingBall();
ball.x = random(100, 200);
ball.y = random(100, 200);
ball.dx = random(-3, 3);
ball.dy = random(-3, 3);
ball.diam = random(50, 150);
ball.fillColor = color(random(255),
random(255),
random(255));
return ball;
}
int NUM_BALLS = 10;
ArrayList<BouncingBall> ballList; // initially null
void setup() {
size(500, 500);
// create the initially empty ArrayList of BouncingBall objects
ballList = new ArrayList<BouncingBall>();
int i = 0;
while (i < NUM_BALLS) {
ballList.add(randomBouncingBall());
i += 1;
}
}
void draw() {
background(255);
// render and update all the balls
for (BouncingBall b : ballList) {
b.render();
b.update();
}
}
void mousePressed() {
BouncingBall b = randomBouncingBall();
b.x = mouseX;
b.y = mouseY;
ballList.add(b);
}