Lesson 2
Module 2 — Control Flow & Repetition

Loops

Computers are great at repeating things — millions of times without getting tired. Loops are how you tell them to do it.

condition still true? run the block false → stop
🔁 while 🔄 do-while 🔢 for ⛔ break & continue
Lesson 4 — while & do-while

Why Repetition Matters

Without loops, you'd have to write the same line of code thousands of times. Loops let you say it once and let the computer repeat it.

😩 Without a loop — printing 1 to 5:

System.out.println(1); System.out.println(2); System.out.println(3); System.out.println(4); System.out.println(5); // What if you needed 1 to 1,000,000?

✅ With a loop — same result, one idea:

int i = 1; while (i <= 5) { System.out.println(i); i++; } // Change 5 to 1_000_000 — done.
🎮

Game loops

Every game runs a loop — check input, update state, draw screen — thousands of times per second.

📋

Processing data

Go through every student's grade, every order in a store, every message in an inbox.

Waiting for input

Keep asking the user for a valid answer until they give one — a natural loop.

Lesson 4 — while loop

The while Loop

Repeat a block of code as long as a condition stays true. Check the condition before each iteration.

// Anatomy of a while loop while ( condition ) { // body — runs if condition is true // must eventually make condition false! } // Example: count down from 5 int count = 5; while (count > 0) { System.out.println(count); count--; // ← moves toward false } System.out.println("Blast off! 🚀");
Output: 5 → 4 → 3 → 2 → 1 → Blast off! 🚀
count = 5 count > 0 ? true println(count) count-- loop back false Blast off! 🚀
Lesson 4 — do-while loop

The do-while Loop

Like a while loop — but the body runs at least once before the condition is ever checked.

// Anatomy do { // body runs first, THEN condition checked } while ( condition ); // ← note semicolon! // Great for: "ask until valid" Scanner sc = new Scanner(System.in); int guess; do { System.out.print("Enter 1–10: "); guess = sc.nextInt(); } while (guess < 1 || guess > 10); System.out.println("Valid: " + guess);
The user must type something before we can check if it's valid — do-while is the natural fit here.

while — checks first

If the condition starts false, the body never runs. Use when you might not need to run at all.

do-while — runs first

Body always runs at least once, then checks. Use when you need to do something before you can decide to continue.

Real-world examples

Menu systems, input validation, game rounds — anywhere the user must act before the program can decide what to do next.

Lesson 4 — Common Bugs

Two Classic Loop Bugs

These will happen to you. Knowing what they look like makes them easy to fix.

🔴 Infinite Loop — never stops

int i = 1; while (i <= 5) { System.out.println(i); // ❌ forgot i++ ! } // prints 1 forever...

Symptoms

Program runs forever, terminal freezes, fan spins up. Fix: press ⌃ C to stop it, then make sure the loop variable actually changes inside the body.

🟡 Off-by-One — one too many or few

// Want to print 1 through 5 int i = 1; while (i < 5) { // ❌ should be <= System.out.println(i); i++; } // only prints 1 2 3 4 — misses 5! // Fix: while (i <= 5) { ... } // ✅

Symptoms

Loop runs one iteration too many or too few. Often caused by using < when you needed <= (or vice versa). Extremely common — even experienced developers make this mistake.

Lesson 4 — Exercise

Exercise: Guessing Game with Retries

Update your guessing game so the player can keep guessing until they get it right.

import java.util.Scanner; public class GuessingGame { public static void main(String[] args) { int secret = 42; Scanner sc = new Scanner(System.in); int guess = 0; int attempts = 0; while (guess != secret) { System.out.print("Guess: "); guess = sc.nextInt(); attempts++; if (guess < secret) System.out.println("Too low!"); else if (guess > secret) System.out.println("Too high!"); } System.out.println( "🎉 Got it in " + attempts + " tries!"); } }

What changed from Lesson 3?

Added a while loop around the guess logic. The loop keeps running until guess == secret.

Tracking attempts

attempts++ increments a counter each iteration — the loop naturally counts how many tries it took.

Challenge

Add a max of 7 guesses. If the player doesn't guess in 7 tries, reveal the answer. Hint: add && attempts < 7 to the condition.

Lesson 5 — for loop

The for Loop

When you know exactly how many times to repeat, for packs the setup, condition, and update into one tidy line.

for ( int i = 0 ① init ; i < 5 ② condition ; i++ ③ update ) { println(i); ④ body }
// Print 0 through 4 for (int i = 0; i < 5; i++) { System.out.println(i); } // Output: 0 1 2 3 4 // Count down for (int i = 10; i >= 1; i--) { System.out.print(i + " "); } // Output: 10 9 8 7 6 5 4 3 2 1 // Count by 2s for (int i = 0; i <= 10; i += 2) { System.out.print(i + " "); } // Output: 0 2 4 6 8 10

① Init — runs once

Creates the loop variable before the first iteration. Usually int i = 0. The variable only exists inside the loop.

② Condition — checked before each iteration

If false, the loop ends immediately. Same as a while loop's condition.

③ Update — runs after each iteration

Usually i++ to move forward, but can be any expression — i--, i += 2, etc.

Lesson 5 — for vs while

When to Use for vs while

Both can do the same job — but one is usually a better fit depending on what you know upfront.

🔢

Use for when you know the count

You know exactly how many times to loop — iterating over a list, counting from A to B, repeating N times.

// Print a 5-star rating for (int i = 0; i < 5; i++) { System.out.print("⭐"); } // Sum 1 through 100 int sum = 0; for (int i = 1; i <= 100; i++) { sum += i; } System.out.println(sum); // 5050

Use while when count is unknown

You don't know how many times — keep going until some event happens (user input, a condition changes, a file ends).

// Keep asking until "quit" String input = ""; while (!input.equals("quit")) { System.out.print("Command: "); input = sc.nextLine(); } // Read a file line by line while (scanner.hasNextLine()) { process(scanner.nextLine()); }
Lesson 5 — Nested Loops

Nested Loops

A loop inside a loop. The inner loop runs completely for every single iteration of the outer loop.

// Times table (1–5) for (int row = 1; row <= 5; row++) { for (int col = 1; col <= 5; col++) { System.out.printf("%4d", row * col); } System.out.println(); }
1 2 3 4 5 2 4 6 8 10 3 6 9 12 15 4 8 12 16 20 5 10 15 20 25
col=1 col=2 col=3 col=4 col=5 row=1 row=2 row=3 row=4 row=5 1 2 3 4 5 2 4 6 8 10 3 6 9 12 15 4 8 12 16 20 5 10 15 20 25
For a 5×5 grid: outer runs 5 times, inner runs 5 times per outer iteration = 25 total executions of the body.
Lesson 5 — break & continue

break and continue

Two keywords that give you fine-grained control over what a loop does mid-iteration.

⛔ break — exit the loop immediately

// Stop when we find 7 for (int i = 1; i <= 10; i++) { if (i == 7) { System.out.println("Found 7!"); break; // jumps out of the loop } System.out.println(i); } // Output: 1 2 3 4 5 6 Found 7!

Use break when…

You found what you were looking for and there's no point continuing — searching a list, hitting a sentinel value, a game-over condition.

⏭️ continue — skip this iteration only

// Print only odd numbers for (int i = 1; i <= 10; i++) { if (i % 2 == 0) { continue; // skip evens } System.out.println(i); } // Output: 1 3 5 7 9

Use continue when…

You want to skip certain items but keep looping — filtering out invalid data, skipping blank lines, ignoring certain values in a calculation.

Lesson 5 — for-each

The for-each Loop

A cleaner syntax for looping over every item in a collection — no index variable needed.

// Regular for — needs index management int[] scores = {90, 85, 72, 95, 88}; for (int i = 0; i < scores.length; i++) { System.out.println(scores[i]); } // for-each — same result, cleaner for (int score : scores) { System.out.println(score); } // Read as: "for each score in scores" // Works on Strings too String[] names = {"Alice", "Bob", "Carol"}; for (String name : names) { System.out.println("Hello, " + name + "!"); }

Syntax: type variable : collection

The variable takes on each value in the collection one by one. You declare its type on the left side of the colon.

When to prefer for-each

When you just need each element's value and don't care about the index — reading, printing, summing, searching.

When to stick with for

When you need the index — modifying elements in place, going backwards, skipping by 2s, comparing adjacent elements.

Lesson 5 — Coding Exercise

FizzBuzz

A classic programming challenge. Simple rules, great practice for loops and conditions working together.

📋 The Rules

Write a program that prints every number from 1 to 100, but:

  • If the number is divisible by 3, print "Fizz" instead
  • If divisible by 5, print "Buzz" instead
  • If divisible by both, print "FizzBuzz"
  • Otherwise, just print the number

🧪 Expected output (first 20)

1 2 Fizz 4 Buzz Fizz 7 8 Fizz Buzz 11 Fizz 13 14 FizzBuzz 16 17 Fizz 19 Buzz

💡 Hint

Use the % (modulo) operator to check divisibility. n % 3 == 0 means n is divisible by 3. Check FizzBuzz first — order matters!

Your starter code:

public class FizzBuzz { public static void main(String[] args) { for (int i = 1; i <= 100; i++) { // your logic here } } }

🏆 Stretch challenges

1. Add a counter — print how many FizzBuzzes there were at the end
2. Make it go 1 to N where N is entered by the user (Scanner)
3. Add a 4th rule: divisible by 7 prints "Bazz"

📁 Create this in ~/Development/labs/lab2/ — use labsmkdir lab2 && cd lab2code .
Recap — Lessons 4 & 5

What You've Covered

🔁

while

Checks condition first. Runs zero or more times. Use when the count is unknown — keep going until something happens.

🔄

do-while

Runs the body first, then checks. Guarantees at least one execution. Ideal for input validation and menus.

🔢

for

Init, condition, update — all in one line. Use when you know the count. Can count up, down, or by any step size.

🗂️

for-each

Cleanest syntax for visiting every element in a collection. No index to manage — just the value.

🐛

Common bugs

Infinite loop — forgot to update the loop variable. Off-by-one — used < when you needed <=.

⛔⏭️

break & continue

break exits the loop entirely. continue skips the rest of this iteration and moves to the next.

🔲

Nested loops

Inner loop runs completely for each outer iteration. Total executions = outer count × inner count. Great for grids and tables.

🚀

Coming up — Lesson 3

Methods — breaking code into reusable named blocks, parameters, return types, and scope.