Looping
For-structure, Loop-until-structure
In this tutorial the goal is to remove items from a sequence that are divisible by two.
for-structure
To start we try using a for-structure:
sequence set = {1,2,3,4,5,6,7,8} for i = 1 to length(set) do if remainder(set[i],2)=0 then set = remove(set, i) end if end for -- error -- subscript value 6 is out of bounds, reading from a sequence of length 4
It is not unreasonable to wish that this example works. The problem is that the for-structure evaluates the loop limits just once and locks them into place. The the sequence keeps changing length; it's like the end of a wagging dog's tail that the for-structure can't keep up with.
You must remember that a for-structure is intended to loop a pre-determined number of times and the limits are fixed before looping commences.
exit keyword
However, you can use the exit keyword to jump out of a for-structure before an error is encountered. Since you know the error is due a "subscript value out of bounds" you can write:
sequence set = {1,2,3,4,5,6,7,8} for i = 1 to length(set) do if remainder(set[i],2)=0 then set = remove(set, i) end if if i>length(set) then exit end if end for ? set --> {1,3,5,7}
backwards
A better solution is to traverse the sequence backwards:
sequence set = {1,2,3,4,5,6,7,8} for i=length(set) to 1 by -1 do if remainder(set[i],2)=0 then set = remove(set, i) end if end for ? set --> {1,3,5,7}
loop-until-structure
Another solution is to use the loop-until-structure were the test condition is recalculated for each iteration:
sequence set = {1,2,3,4,5,6,7,8} integer i=1 loop do if remainder(set[i],2)=0 then set = remove(set, i) end if i += 1 until i > length(set) end loop ? set --> {1,3,5,7}