Search

vendredi 24 mars 2017

Unbounded integers

Context

After 16-bit integers, we can try to implement 32-bit, 64-bit, ... but the principles are the same.
Instead, let's define unbounded integer, in  other word one single integer that has no limit (in other words, an integer that can execute +[+] without never ending).
We will focus on one single integer, because it is far more simple. Actually, any implementation we can imagine will rely on arrays with dynamic sizes. The array can be resized, meaning that the data before and / or after will have to be moved. This is not impossible, but extending one array then means extend one array + move next integer + move integer after this one + move integer after this one + ...
This will be definitely too long (not impossible anyway), so let's just implement one single number like this.

The data structure:

  • A number N will be encoded in an array of cells
  • Encoding will be in base 255
    • Note: not 256. This allows to have values from 1 to 255. Therefore, there won't be any null cell, so no need to have a 2-cells array to browse it. This divides the memory used by 2.
  • Operator overrides will be defined below. However, we will need 2 different overrides for LEFT and RIGHT: one from the number N and one to number N.
  • Data representation:

memory_before [0 0 0 0 D1 D2 D3 .... Dx 0] memory_after
  • By default, cursor will be on first base-255 digit D1.

Process

  • Print: simply print D1. However, the values are between 1 and 255. So
    • Decrease D1
    • Print D1
    • Increase D1
  • Read: idem
    • Reset all digits (set to 1)
    • Read to D1
    • Increase D1
  • Inc:
    • Set loop flag.
    • Start with digit D1 and loop
      • if current digit is null, set to 1
      • increase current digit
      • move before loop flag
      • if not null, reset loop flag
      • otherwise, set to 1 (equivalent to null in our representation)
      • process next digit if loop flag is on
    • Move back values to their position
  • Dec: idem
    • Set loop flag
    • Start with digit D1 and loop
      • if current digit is null, set to 1
      • decrease current digit
      • move before loop flag
      • if not null, reset loop flag
      • otherwise, set to 255
      • process next digit if loop flag is on
    • Move back values to their position
  • While:
    • Our structure is [R 0 0 0 D1 D2 D3 .... Dx 0]
    • We want to check if at least one of the digits is not 1 and store into R
    • Set loop flag
    • Start with D1 and loop
      • Reset loop flag
      • if current digit is not null
        • Set loop flag
        • if digit is not 1 (decrease then while)
          • Set R to 1
          • Reset loop flag
          • Move digit before loop flag
        • increase moved digit to recover initial value (see 4 lines above)
      • process with next digit if loop flag is on
    • Move back values to their position
    • Move to result
    • If not null: enter while, reset result, go to D1
  • Loop
    • Same as while to compute result
    • Move to result
    • If not null: loop
    • Go back to D1
  • Left (from N)
    • 5 cells on the left
  • Left (to N). Note: with unbounded array, it is not recommended to have things after the array
    • 2 cells on left for last digit then go to D1
  • Right (to N)
    • 5 cells on the right
  • Right (from N). Note: again, with unbounded array, going after array in memory is not recommended
    • Go to last digit then 2 cells on the right

Code - print

-.+

Code - read

Go to last integer
[>]<
Set all digits to 1 up to first
[[-]+<]
Read value and increase
>,+

Code - inc

Set loop flag
<+
Loop
[
  Go to current digit
  >
  If current digit is null then initialize to 1
    reset loop flag as else bit
    [<-]
    go to else bit or 0 and if else bit then set digit to 1 and go to 0
    <[->+<<]
    go back to digit and reset loop flag
    >+>
  Increase current digit and move before loop flag
  +[-<<+>>]
  Go to current digit
  <<
  If not null reset loop flag and set to 1 otherwise
  [>-]>[<+>>]
  Move loop flag to left and go to loop flag then loop
  <[->+<]>
]
Go to last moved digit
<<
Move back all digits
[[->>+<<]<]>>>

Code - dec

Set loop flag
<+
Loop
[
  Go to current digit
  >
  If current is null then initialize to 1
    reset loop flag as else bit
    [<-]
    go to else bit or 0 and if else bit then set digit to 1 and go to 0
    <[->+<<]
    go back to digit and reset loop flag
    >+>
  Decrease current digit and move before loop flag
  -[-<<+>>]
  Go to current digit
  <<
  If not null reset loop flag and set to 255 otherwise
  [>-]>[<->>]
  Move loop flag to left and go to loop flag then loop
  <[->+<]>
]
Go to last moved digit
<<
Move back all digits
[[->>+<<]<]>>>

Code - while

Set loop flag
<+
Loop
[
  Reset loop flag and go to current digit
  ->
  If not null: still in the number
  [
    Set loop flat to 1
    <+
    If current digit is not 1
    >-[
      set result to 1
      <<<[<]<+
      reset loop flag
      >>[>]>-
      move digit before flag
      >[-<<+>>]
    ]
    Add 1 to digit copy and go back to location
    <<+>>
  ]
  Move loop flag
  <[->+<]
  Go to loop flag and loop
  >
]
Go to last moved digit (can be 2 or 3 cells on the left)
<<[>]<
Move back all digits
[[->>+<<]<]
Go to result and start while
<[
  Reset result and move back to first digit
  ->>>>

Code - loop

Set loop flag
<+
Loop
[
  Reset loop flag and go to current digit
  ->
  If not null: still in the number
  [
    Set loop flat to 1
    <+
    If current digit is not 1
    >-[
      set result to 1
      <<<[<]<+
      reset loop flag
      >>[>]>-
      move digit before flag
      >[-<<+>>]
    ]
    Add 1 to digit copy and go back to location
    <<+>>
  ]
  Move loop flag
  <[->+<]
  Go to loop flag and loop
  >
]
Go to last moved digit (can be 2 or 3 cells on the left)
<<[>]<
Move back all digits
[[->>+<<]<]
Go to result and loop if needed
<]
Move back to initial position
>>>>

Code - left from N

<<<<<

Code - left to N

<<[<]>

Code - right to N

>>>>>

Code - right from N

[>]>

Example - try it

This code is equivalent to +[.+] with unbounded integers

>>>>++<+[->[<+>-[<<<[<]<+>>[>]>->[-<<+>>]]<<+>>]<[->+<]>]<<[>]<[[->>+<<]<]<[->>>>-.+<+[>[<-]<[->+<<]>+>+[-<<+>>]<<[>-]>[<+>>]<[->+<]>]<<[[->>+<<]<]>>><+[->[<+>-[<<<[<]<+>>[>]>->[-<<+>>]]<<+>>]<[->+<]>]<<[>]<[[->>+<<]<]<]>>>>

1 commentaire:

  1. Hey man, who are you? I'd like to contact you. I made a brainfuck version of the Arduino :)
    Check it out: https://youtu.be/QloNq8AoHvU

    RépondreSupprimer