Iterate
- Not to be confused with ITERATE.
Iterate is a Turing complete programming langugage invented by User:Aadenboy which only uses iterative loops.
Syntax
Since Iterate is not programmer-friendly, a more convenient version which can be compiled into Iterate code is documented at Iterate/Compilation.
Loops
Loops are initialized with an asterisk (optionally with a number preceding it surrounded by parentheses), followed by the amount of times it loops, then the loop itself. There are only loops. Outside of a loop, its index is zero.
| Code | Definition |
|---|---|
*#< ... >
|
Loop # times. If it is zero or nothing, don't run. The visit count will still accumulate regardless of whether or not it had looped. |
*∞< ... >
|
Loop forever. |
*< ... >
|
Skip the code inside. |
(#*)...< ... >
|
A labeled loop for future reference. # must be a number. Different loops can share a single label if they are within separate scopes. |
(*)...< ... >
|
The main loop. This must enclose the entire program. |
A visit is defined as every time the program encounters a loop or label, regardless of whether or not the body actually runs. Note the difference between loops and labels, as labels can be shared across loops, so long as a label only appears once within its scope.
Loop amounts
You are able to provide different loop amounts via referencing other loops, or by a constant. A loop many only use one amount.
| Code | Definition |
|---|---|
| Number | That many times. |
∞
|
Infinity. |
?
|
Advances the cursor to and uses the first string of numbers to the right of the cursor, or to EOF with 0 if there is none. |
~?
|
Parses the next bytes as a UTF-8 character, returning the codepoint. If it is invalid, it is equivalent to zero and all invalid bytes are skipped. |
%?
|
Returns the next byte. |
n
|
The current index of the parent loop. This equals zero for the main loop's parent. |
n#
|
The current index of label #. This equals zero if the label doesn't exist. |
n^
|
The current index of the main loop. |
~n
|
How many loops are left until the parent loop's final loop. This equals zero for the main loop's parent. |
~n#
|
The above command, but with a label. This equals zero if the label doesn't exist. |
~n^
|
The above command, but with the main loop. |
=
|
How many times the parent loop was visited. This is not the same as how many times a label was visited. This equals zero for the main loop's parent. |
=#
|
How many times a label was visited. This is not the same as how many times a certain loop was visited. This equals zero if the label doesn't exist. |
=^
|
The above command, but with the main loop. Usually equal to one unless you explicitly reset it. |
For the input values(?, ~?, and %? when using CLI input, all the characters inputted are added to a buffer that is parsed like in the file case. Further invocations of ?, ~?, or %? use the buffer instead of another IO read until it is empty. The buffer will always end in the NULL character (U+0000) after being filled. ? will automatically re-prompt if there are no more numbers in the buffer.
Commands
These are placed in a loop.
| Code | Definition |
|---|---|
!
|
Immediately break out of the parent loop. Analogous to break.
|
!#
|
Immediately break out of label # IF you are inside it. This is a no-op if otherwise. |
!^
|
Stop execution. |
&
|
Skip to the end of the parent loop. Analogous to continue.
|
&#
|
Skip to the end of label # IF you are inside it. This is a no-op if otherwise. |
&^
|
Skip to the end of the main loop. |
@
|
Output the current index of the parent loop as a number. |
~@
|
Output the current index of the parent loop as a UTF-8 formatted character. |
%@
|
Output the current index in byte form, mod 256. |
$
|
Reset the visit count of the parent loop. |
$#
|
Reset the visit count of label #. |
$^
|
Reset the visit count of the main loop. |
Completeness
Iterate is Turing complete. See Iterate/Turing-completeness proof.
Without any ability to reset visit counts, Iterate is most likely equivalent to ITERATE.
Basic arithmetic
For a complete list of mathematical operations and other algorithms, see Iterate/Library.
A+B
(*)1<
*?< (1*)<> > // increment L1
*?< (1*)<> > // increment L1 again
(2*)=1< // output character
*~n< &2 > // skip to prevent early prints
@
!^ // end early to avoid printing 0 case
>
(3*)48< // print 0 as its ASCII code (48)
*~n< &3 > // skip to prevent early prints
~@
>
>
A-B
Note: Results lower than one will not output anything.
(*)1<
*?< (1*)<> > // L1 = A
*?< // decrement L1 by one B times
$2
*=1< // store L1-1 in L2
*~n< (2*)<> > // ~n acts as L1-1
!
>
$1
*=2< (1*)<> > // copy from L2 to L1
>
(3*)=1< // output character
*~n< &3 > // skip to prevent early prints
@
!^ // end early to avoid printing 0 case
>
(4*)48< // print 0 as its ASCII code (48)
*~n< &4 > // skip to prevent early prints
~@
>
>
A*B
(*)1<
*?< (1*)<> > // store A to L1
*?< (2*)<> > // store B to L2
*=1<
*=2<
(3*)<> // visited A*B times as an intrinsic property of nested loops
>
>
(4*)=3< // output character
*~n< &4 > // skip to prevent early prints
@
!^ // end early to avoid printing 0 case
>
(5*)48< // print 0 as its ASCII code (48)
*~n< &5 > // skip to prevent early prints
~@
>
>
A%B
(*)1<
*?< (1*)<> > // L1 = A
*?< (2*)<> (4*)<> > // L2 = B, L4 = B
(6*)=1< // increment L3 to equal L1
(3*)<> // L3 = L3 + 1
$5
*=4< (5*)<> > // L5 = L4
$4
*=5<
*~n< (4*)<> > // L4 = L5 - 1
!
>
*=4< &6 > // if L4 == 0 (or when modulus returns 0)...
$3 // L3 = 0
*=2< (4*)<> > // L4 = L2 (reset count)
>
(7*)=3< // print result
*~n< &7 > // skip to prevent early prints
@
!^ // end early to avoid printing 0 case
>
(8*)48< // print 0 as its ASCII code (48)
*~n< &8 > // skip to prevent early prints
~@
>
>
A/B
The same algorithm can be used to calculate floored division.
(*)1<
*?< (1*)<> >
*?< (2*)<> (4*)<> >
(6*)=1< // a%b algorithm
(3*)<>
$5
*=4< (5*)<> >
$4
*=5<
*~n< (4*)<> >
!
>
*=4< &6 >
$3
*=2< (4*)<> >
(7*)<> // count how many times L3 resets for the quotient
>
(10*)1<
(8*)=7< // print quotient
*~n< &8 >
@
!10
>
(9*)48<
*~n< &9 >
~@
>
>
(11*)82< // "R"
*~n< &11 >
~@
>
(12*)=3< // print remainder
*~n< &12 >
@
!^
>
(13*)48<
*~n< &13 >
~@
>
>
Conditionals
While this code checks if A == B, you can trivially modify it to check for A < B, A > B, and any combination or negation of those cases.
(*)1<
*?< (1*)<> > // L1 = A
*?< (2*)<> > // L2 = B
// L7 will hold if A == B: 1 = true, 0 = false
// we'll continuously decrement A and B until either reaches 0
// if either reaches 0 first before the other, they're not equal
// otherwise they are equal
(5*)∞<
(6*)1< // we check FIRST for the edge case where either A or B starts as 0
*=1<
*=2< !6 > // case 1: neither A nor B are 0 -> continue
!5 // case 2: B reached 0 first -> A > B
>
*=2<
*=1< !6 > // case 1: neither A nor B are 0 -> continue
!5 // case 3: A reached 0 first -> A < B
>
(7*)<> // case 4: both reached 0 at the same time -> A == B
!5
>
$3
$4
*=1< (3*)<> > // L3 = L1
*=2< (4*)<> > // L4 = L2
$1
$2
*=3< *~n< (1*)<> > ! > // L1 = L3 - 1
*=4< *~n< (2*)<> > ! > // L2 = L4 - 1
>
*=7< @ !^ > // print 1 if true
(8*)48< // print 0 if false
*~n< &8 >
~@
>
>
Arbitrary memory
Arbitrary memory can be implemented with a single label using arbitrary memory emulation.
Example programs
Hello, world!
(*)1<
*1< (1*)72< *~n< &1 > ~@ ! > > // H
*1< (1*)101< *~n< &1 > ~@ ! > > // e
*1< (1*)108< *~n< &1 > ~@ ~@ // ll
*1< (2*)111< *~n< &2 > ~@ // o
*1< (3*)44< *~n< &3 > ~@ ! > > // ,
*1< (3*)32< *~n< &3 > ~@ ! > > //
*1< (3*)119< *~n< &3 > ~@ ! > > // w
~@ ! > > // o
*1< (2*)114< *~n< &2 > ~@ ! > > // r
~@ ! > > // l
*1< (1*)100< *~n< &1 > ~@ ! > > // d
*1< (1*)33< *~n< &1 > ~@ ! > > // !
>
Cat program
(*)∞<
(1*)~?< // read a character
*~n< &1 > // skip forwards until the index equals the codepoint
~@ // output the character
&^ // continue past the break
>
! // if it was zero, there's no more input and it stops executing
>
Reverse cat
Using AME. This does not handle UTF-8.
(*)1<
(4*)∞< // read loop
$1
*%?< (1*)<> > // get the next byte
*=1< // shift the stack
$3
*256< *=2< (3*)<> > > // shift by multiplying by 256
$2
*=3< (2*)<> > // update L2
!
>
*=1< (2*)<> > // push the byte onto the stack
*=1< &4 > // continue if there was a byte
! // stop reading if there are no more bytes
>
(5*)∞< // write loop
*256< (6*)<> (8*)<> > // byte length is 256
(10*)=2< // pop from the stack by dividing by 256
(7*)<>
$9
*=8< (9*)<> >
$8
*=9<
*~n< (8*)<> >
!
>
*=8< &10 >
$7 // remainder is the popped byte
*=6< (8*)<> >
(11*)<> // quotient is the remaining stack
>
(8*)=7< // print the byte
*~n< &8 >
%@
$2
*=11< (2*)<> > // update the stack
$6 $7 $8 $9 $10 $11 // reset
&5
>
! // if the byte was 0, stop writing
>
>
Truth-machine
(*)1<
*?< // if input were to be 0, this wouldn't run
*∞< // loop forever
*1< @ > // loop for index of 1 printed
>
>
(1*)48< // printing 0 as its ASCII code (48)
*~n< &1 > // skip to prevent early prints
~@
>
>
Looping counter
(*)∞<
*n<
(1*)42<
*~n< &1 >
~@
>
>
(1*)10<
*~n< &1 >
~@
>
>
Triangular numbers
(*)∞<
*n<
*~n<
(1*)<>
>
!
>
(4*)1<
(2*)=1<
*~n< &2 >
@
!4
>
(3*)48<
*~n< &3 >
~@
>
>
(5*)10<
*~n< &5 >
~@
>
>
FizzBuzz
(*)∞<
$1 $2 $3 $4 $5 $6 $7 $8 $9 $12
*n^< (1*)<> >
*3< (4*)<> (5*)<> > // mod 3
*5< (6*)<> (7*)<> > // mod 5
*=1< // calculates mod 3 and mod 5 at the same time
(2*)<>
(3*)<>
$8 $9
*=5< (8*)<> >
*=7< (9*)<> >
$5 $7
*=8< *~n< (5*)<> > ! >
*=9< *~n< (7*)<> > ! >
*1< (10*)1<
*=5< &10 >
$2
*=4< (5*)<> >
> >
*1< (10*)1<
*=7< &10 >
$3
*=6< (7*)<> >
> >
>
*1< (11*)1< // if mod 3 == 0
*=2< !11 >
*1< (12*)70< *~n< &12> ~@ > > // F
*1< (12*)105< *~n< &12> ~@ > > // i
*1< (12*)122< *~n< &12> ~@ ~@ > > // zz
> >
*1< (11*)1< // if mod 5 == 0
*=3< !11 >
*1< (12*)66< *~n< &12> ~@ > > // B
*1< (12*)117< *~n< &12> ~@ > > // u
*1< (12*)122< *~n< &12> ~@ ~@ > > // zz
> >
(13*)n< // print number if neither condition was met
*=12< !13 >
*~n< &13 >
@
>
(14*)10< // newline
*~n< &14 >
~@
>
>