Loops 3 - Using the for-loop

Level 1 - the basics

Copy this fragment to the run() method of an exercise in IntelliJ.

SaxionApp.printLine("Before the for-loop starts");
for (int i = 0; i < 10; i++) {
    SaxionApp.printLine("In the loop, the value of i is " + i);
    SaxionApp.sleep(0.2);
}
SaxionApp.printLine("The for-loop has finished");

Run the code. You should see appearing the texts. How many times does "In the loop..." appear? Change the code so the message "In the loop..." appears 20 times.

SaxionApp.printLine("Before the for-loop starts"); for (int i = 0; i < 20; i++) { SaxionApp.printLine("In the loop, the value of i is " + i); SaxionApp.sleep(0.2); } SaxionApp.printLine("The for-loop has finished");

Please note the first and last number of i. Can you explain this based on the code?

Change the code, so that i takes steps of 2 instead of 1.

SaxionApp.printLine("Before the for-loop starts"); for (int i = 0; i < 20; i=i+2) { SaxionApp.printLine("In the loop, the value of i is " + i); SaxionApp.sleep(0.2); } SaxionApp.printLine("The for-loop has finished");

What is the last value of i that is printed?

Now change the code so that the for-loops runs backwards, from 10 to (including) 1.

SaxionApp.printLine("Before the for-loop starts"); for (int i = 10; i > 0; i--) { SaxionApp.printLine("In the loop, the value of i is " + i); SaxionApp.sleep(0.2); } SaxionApp.printLine("The for-loop has finished");

Note, the i > 0 construction in the solution. This means that this condition is true, for values from 1 and up.

Try to write and alternative solution for the above exercise, by only changing the condition in the for loop.

SaxionApp.printLine("Before the for-loop starts"); for (int i = 10; i >= 1; i--) { SaxionApp.printLine("In the loop, the value of i is " + i); SaxionApp.sleep(0.2); } SaxionApp.printLine("The for-loop has finished");

Note the i >= 1 actually does the same as i > 0.

Level 2 - For loop and a list

Copy the above code in a projects run() method. Run the code, and look at the result.

ArrayList names = new ArrayList();
names.add("Lisa");
names.add("Bart");
names.add("Marge");
names.add("Homer");
names.add("Skinner");

for (int i = 0; i < 5; i++) {
    String name = names.get(i);
    SaxionApp.printLine(name);
}

Are all names printed? Now add another name to the list, for instance "Mr. Burns". Run the code again, what do you see?

Now update code so that all the names are printed.

ArrayList<String> names = new ArrayList<String>(); names.add("Lisa"); names.add("Bart"); names.add("Marge"); names.add("Homer"); names.add("Skinner"); names.add("Mr. Burns"); for (int i = 0; i < 6; i++) { String name = names.get(i); SaxionApp.printLine( name ); }

You might have changed the code, by changing the 5 into a 6 in the for-loop condition. Or you might have changed < into `<=``. Both result in a working solution, but they are not ideal. Preferably you do not want to have to update your code, based on the number of items in a list. Suppose the number of items in the list depends on the input of the user and you don't know the number of items in the list before-hand. The only solution is then to make the loop condition 'dynamic' and based on the actual size of the list.

Now update the code, so that the for-loop condition will use the size of the list and prints all items.

ArrayList<String> names = new ArrayList<String>(); names.add("Lisa"); names.add("Bart"); names.add("Marge"); names.add("Homer"); names.add("Skinner"); names.add("Mr. Burns"); for (int i = 0; i < names.size(); i++) { String name = names.get(i); SaxionApp.printLine(name); }

Are all the names printed? And are all names printed if you add another name to the list?

Note: With loops in combination with lists, you have common alternatives for looping through all the items in the list.

  1. for (int i = 0; i < names.size(); i++)
  2. for (int i = 0; i <= names.size() - 1; i++)

Where the first option is mostly used.

Level 2 - Calculations

Now, let's use a list with numbers. Copy this fragment again to the run() method of an exercise in IntelliJ.

ArrayList numbers = new ArrayList();
numbers.add(10);
numbers.add(20);
numbers.add(30);
numbers.add(40);
numbers.add(50);

for (int i = 0; i < numbers.size(); i++) {
    int number = numbers.get(i);
    SaxionApp.printLine(number);
}

Are all the numbers printed? Good. Often, you will need to do some calculations on a list with numbers. Change the code so that all the numbers are added together and the sum (should be 150) is printed.

ArrayList<Integer> numbers = new ArrayList<Integer>(); numbers.add(10); numbers.add(20); numbers.add(30); numbers.add(40); numbers.add(50); int sum = 0; for (int i = 0; i < numbers.size(); i++) { sum = sum + numbers.get(i); } SaxionApp.printLine("The sum is: " + sum);

Does this solution still work if a number is added to the list? Can you still explain why this is? Note, that numbers.get(i) is not seperately stored in a new variable anymore.

Change the code so that the average of the numbers is printed.

ArrayList<Integer> numbers = new ArrayList<Integer>(); numbers.add(10); numbers.add(20); numbers.add(30); numbers.add(40); numbers.add(50); int sum = 0; for (int i = 0; i < numbers.size(); i++) { sum = sum + numbers.get(i); } double average = (double)sum / numbers.size(); SaxionApp.printLine("The average is: " + average + " or directly :" + ((double)sum / numbers.size()));

Now add the numbers 1 up to 5 to the list and only print the even numbers. Change the code to achieve this.

ArrayList<Integer> numbers = new ArrayList<Integer>(); numbers.add(1); numbers.add(2); numbers.add(3); numbers.add(4); numbers.add(5); for (int i = 0; i < numbers.size(); i++) { if (numbers.get(i) % 2 == 0) { SaxionApp.printLine("This is an even number:" + numbers.get(i)); } }

Since the combination of for-loops and lists are so often used, you can use a short-hand notation for this. Please copy the code below.

ArrayList numbers = new ArrayList();
numbers.add(1);
numbers.add(2);
numbers.add(3);
numbers.add(4);
numbers.add(5);

for (Integer number: numbers) {
    SaxionApp.printLine("Item:" + number);
}

This is the syntax for an enhanced for loop. for (Integer number: numbers) {...} It has the following items:

Now copy the code below to your run() method.

ArrayList names = new ArrayList();
names.add("Lisa");
names.add("Bart");
names.add("Marge");
names.add("Homer");
names.add("Skinner");

for (int i = 0; i < names.size(); i++) {
    String name = names.get(i);
    SaxionApp.printLine( name );
}

This code still uses a regular for-loop. Now update the code to use a enhanced for-loop.

ArrayList<String> names = new ArrayList<String>(); names.add("Lisa"); names.add("Bart"); names.add("Marge"); names.add("Homer"); names.add("Skinner"); for (String name: names) { SaxionApp.printLine( name ); }

Allthough this code is shorter and cleaner. Can you also think of drawbacks?

// 1. A drawback could be that in enhanced for-loop you do not have access to the loop counter. // And a loop counter can for instance be used the print the position of the item in the list // 2. Another drawback is that (by default) the complete list is iterated and you might not want that.

Level 3 - Using a while-loop or a for-loop?

Everything you can achieve with a for-loop, you can also achieve with a while-loop and vice-versa. In order to 'prove' this rewrite the while loop example below to make use of a for-loop.

ArrayList names = new ArrayList();
names.add("Lisa");
names.add("Bart");
names.add("Marge");
names.add("Homer");
names.add("Skinner");

int counter = 0;
while (counter < names.size()) {
    String name = names.get(counter);
    SaxionApp.printLine(name + " is on list position:" + counter);

    counter = counter + 2; // Note the +2
}

ArrayList<String> names = new ArrayList<String>(); names.add("Lisa"); names.add("Bart"); names.add("Marge"); names.add("Homer"); names.add("Skinner"); for (int i = 0; i < names.size(); i = i + 2) { String name = names.get(i); SaxionApp.printLine(name + " is on list position:" + i); }

In the examples above using a for-loop or enhanced for-loop makes perfect sense. The reason for this is that you know how many iterations the for-loop should perform. That is as many iterations as there are items in a list. If you don't know this beforehand, a while loop is a better option. An example in which a while loop is preffered, can be found below.

SaxionApp.printLine("Make a choice and type 'stop' to stop");
String userInput = SaxionApp.readString();

while (!userInput.equals("stop")) {
    // Do something here...
    
    SaxionApp.printLine("Make a choice and type 'stop' to stop");
    userInput = SaxionApp.readString();
}

This could be rewritten using a for loop, but this leads to strange code, so using while is the better option.