|REBOL 3 Docs||Guide||Concepts||Functions||Datatypes||Errors|
|TOC < Back Next >||Updated: 18-Apr-2009 Edit History|
The purpose of this section is to provide a summary of how loops are created.
The loop function is the simplest way to evaluate a block a given number of times.
loop 3 [print "Hello world"] Hello world Hello world Hello world
The loop function returns the value of the final evaluation of the block:
i: 0 print loop 40 [i: i + 10] 400
The repeat function's first argument is a word that will be used to hold the count value:
repeat count 3 [print ["count:" count]] count: 1 count: 2 count: 3
Notice that repeat is one-based. The counter begins at one, not zero.
The final block value is also returned:
i: 0 print repeat count 10 [i: i + count] 55
The for function is rarely used in REBOL code, because other types of loops are easier to write. However, for basically extends repeat by allowing a starting value, the ending value, and specification of the increment amount.
The example below begins at zero and counts to 50, incrementing by 10 each time through the loop:
for count 0 50 10 [print count] 0 10 20 30 40 50
Notice that the for function iterates the loop up to and including the ending value. However, if the count exceeds the ending value, the loop is terminated. The example below specifies an ending value of 55. That value will never be hit because the loop increments by 10 each time. The loop stops at 50.
for count 0 55 10 [prin [count " "]] 0 10 20 30 40 50
The next example shows how to count down. It begins at four and counts down to zero one at a time.
for count 4 0 -1 [print count] 4 3 2 1 0
The for function also works for decimal numbers, money, times, dates, series, and characters. Be sure that both the starting and ending values are of the same datatype. Here are several examples of using the for loop with other datatypes.
for count 10.5 0.0 -1 [prin [count " "]] 10.5 9.5 8.5 7.5 6.5 5.5 4.5 3.5 2.5 1.5 0.5
for money $0.00 $1.00 $0.25 [prin [money " "]] $0.00 $0.25 $0.50 $0.75 $1.00
for time 10:00 12:00 0:20 [prin [time " "]] 10:00 10:20 10:40 11:00 11:20 11:40 12:00
for date 1-jan-2000 4-jan-2000 1 [prin [date " "]] 1-Jan-2000 2-Jan-2000 3-Jan-2000 4-Jan-2000
for char #"a" #"z" 1 [prin char] abcdefghijklmnopqrstuvwxyz
The for function also works on series. The following example uses for on a string value. The word end is defined as the string with its current index at the d character. The for function moves through the string series one character at a time and stops when it reaches the character position defined to end:
str: "abcdef" end: find str "d" for s str end 1 [print s] abcdef bcdef cdef def
The foreach function provides a convenient way to repeat the evaluation of a block for each element of a series. It works for all types of block and string series.
In the example below, each word in the block will be printed:
colors: [red green blue] foreach color colors [print color] red green blue
In the next example, each character in a string will be printed:
string: "REBOL" foreach char string [print char] R E B O L
In the example below, each filename in a directory block will be printed:
files: read %. foreach file files [ if find file ".t" [print file] ] file.txt file2.txt newfile.txt output.txt
When a block contains groups of values that are related, the foreach function can fetch all the values of the group at the same time. For example, here is a block that contains a time, string, and price. By providing the foreach function with a block of words for the group, each of their values can be fetched and printed.
movies: [ 8:30 "Contact" $4.95 10:15 "Ghostbusters" $3.25 12:45 "Matrix" $4.25 ] foreach [time title price] movies [ print ["watch" title "at" time "for" price] ] watch Contact at 8:30 for $4.95 watch Ghostbusters at 10:15 for $3.25 watch Matrix at 12:45 for $4.25
In the above example, the foreach value block, [''time title price], specifies that three values are to be fetched from movies for each evaluation of the block.
The variables used to hold the foreach values are local to the block. Their value are only set within the block that is being repeated. Once the loop has exited, the variables return to their previously set values.
Similar to foreach, the forall function evaluates a block for every value in a series. However, there are some important differences. The forall function is handed the series that is set to the beginning of the loop. As it proceeds through the loop, forall modifies the position within the series.
colors: [red green blue] forall colors [print first colors] red green blue
In the above example, after each evaluation of the block, the series is advanced to its next position. When forall returns, the color index is at the tail of the series.
To continue to use the series you will need to return it to its head position with the following line:
colors: head colors
Like forall, forskip is handed the series with the series index set to where it is to begin. Then, forskip modifies the index position as it continues the loop. After each evaluation of the body block, the series index is advanced by the skip amount to its next index position. The following example demonstrates forskip :
movies: [ 8:30 "Contact" $4.95 10:15 "Ghostbusters" $3.25 12:45 "Matrix" $4.25 ] forskip movies 3 [print second movies] Contact Ghostbusters Matrix
The following example uses forever to check for the existence of a file every ten minutes:
forever [ if exists? %datafile [break] wait 0:10 ]
The until function repeats a block until the evaluation of the block returns true (that is, not false or none! ). The evaluation block is always evaluated at least once. The until function returns the value of its block.
The example below will print each word in the color block. The block begins by printing the first word of the block. It then moves to the next color for each color in the block. The tail? function checks for the end of the block, and will return true, which will cause the until function to exit.
color: [red green blue] until [ print first color tail? color: next color ] red green blue
The while function repeats the evaluation of its two block arguments while the first block returns true. The first block is the condition block, the second block is the evaluation block. When the condition block returns false or none!, the expression block will no longer be evaluated and the loop terminates.
Here is a similar example to that show above. The while loop will continue to print a color while there are still colors to print.
color: [red green blue] while [not tail? color] [ print first color color: next color ] red green blue
The condition block can contain any number of expressions, so long as the last expression returns the condition. To illustrate this, the next example adds a print to the condition block. This will print the index value of the color. It will then check for the tail of the color block, which is the condition used for the loop.
color: [red green blue] while [ print index? color not tail? color ][ print first color color: next color ] 1 red 2 green 3 blue 4
The last value of the block is returned from the while function.
A break can be used to escape from the loop at any time.
You can stop the repeated evaluation of a block with the break function. The break function is useful when a special condition is encountered and the loop must be stopped. The break function works with all types of loops.
In the following example, the loop will break if a number is greater than 5.
repeat count 10 [ if (random count) > 5 [break] print "testing" ] testing testing testing
The break function does not return a value from the loop unless a /return refinement is used:
print repeat count 10 [ if (random count) > 5 [break/return "stop here"] print "testing" "normal exit" ] testing testing testing stop here
In the above example, if the repeat terminates without the condition occurring, the block returns the string normal exit. Otherwise, break/return will return the string stop here.
The continue function will cause a loop to jump back to the top.
Editor note: This section is new or has has recently changed and is still under construction.
|TOC < Back Next >||REBOL.com - WIP Wiki||Feedback Admin|