Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Combine variables and operators #1

Open
mcspr opened this issue Sep 2, 2020 · 3 comments
Open

Combine variables and operators #1

mcspr opened this issue Sep 2, 2020 · 3 comments
Labels
enhancement New feature or request

Comments

@mcspr
Copy link
Owner

mcspr commented Sep 2, 2020

Also, allow to use:

  • &operator to create function reference (with specific 'callable' internal type). allow to postpone the operator call:
    $var &some &operator ifn call
    (note that $bla &operator &value ifn is also theoretically possible, while not making any real sense :)
  • $operator (?) i.e. deref support. this might store operator object pointer as unsigned. not very useful, as it seems at a first glance
  • simplify 'constant' words like nan and pi
@mcspr mcspr added the enhancement New feature or request label Sep 2, 2020
@mcspr
Copy link
Owner Author

mcspr commented Sep 20, 2020

Looking at the TON's fift:
https://test.ton.org/fiftbase.pdf, '3.1 Defining and executing blocks`

I wonder if this addition would also be helpful:

dup dup $condition { + + } { - - } if

Introducing another stack element - another stack. Parser will still go over the contents (and obviously parse nested blocks as well), so we never ignore the invalid syntax and / or operators that are missing. Insides of { ... } are stored in-place as rpn_value objects and operator pointers. In the example above, if will 'apply' the block contents onto the current stack.

How to implement this is another question, since operators would need to be aware of such addition without requiring us to re-write every each one to include 'isStack()'. Perhaps, as strong type requirement in the set_operator() in addition to the argc.
(fift source might be helpful, but not very much b/c of different approach to value storage and being more close to Forth with different 'types' of words)

As a possible idea - introduce another stack instead of abusing the existing one with myriads of conditional checks. ifn right now works on values, if might only work on such block stack i.e. require block stack size 2 and value stack size 1.

@mcspr
Copy link
Owner Author

mcspr commented Sep 21, 2020

As a POC, the following works:
master...poc/blocks

>>> { 1 { 1 + } }
REASON: Main DEPTH: 1
004: 002: 4 (Unsigned)  (BLOCK SIZE)
003: 003: 2 (Unsigned)  (BLOCK SIZE)
002: 003: + (String)  (OPERATOR NAME)
001: 003: 1 (Float)  (VALUE)
000: 002: 1 (Float)  (VALUE)

>>> interpret
REASON: Main DEPTH: 1
003: 002: 2 (Unsigned)  (BLOCK SIZE)
002: 002: + (String)  (OPERATOR NAME)
001: 002: 1 (Float)  (VALUE)
000: 002: 1 (Float)  (VALUE)

>>> interpret
REASON: Main DEPTH: 1
000: 000: 2 (Float)  (VALUE)

Counting depth is another issue. Right now stack value has additional counter byte which is added after stack pop an also after the interpret, when the value is simply passed along as-is.

@mcspr
Copy link
Owner Author

mcspr commented Sep 22, 2020

upd: with fixed block enumeration and removed restriction on doing [ & ] inside of the block, the following structure is now allowed:

>>> { 1 2 3 [ 1 1 + ] + + + + }
REASON: Main DEPTH: 1
009: 001: 9 (Unsigned)  (BLOCK SIZE)
008: 001: + (String)  (OPERATOR NAME)
007: 001: + (String)  (OPERATOR NAME)
006: 001: + (String)  (OPERATOR NAME)
005: 001: + (String)  (OPERATOR NAME)
004: 002: 1 (Unsigned)  (ARRAY SIZE)
003: 002: 2 (Float)  (VALUE)
002: 001: 3 (Float)  (VALUE)
001: 001: 2 (Float)  (VALUE)
000: 001: 1 (Float)  (VALUE)

>>> interpret
REASON: Main DEPTH: 1
000: 000: 9 (Float)  (VALUE)

Additional operators should follow - if ('condition for_true for_false if') and : ('block name :') and allowing 'word' search for operators to search for such created words as well.


Another interesting thing from classic forth, which is also available in fift:

: plus-one 1 + ;
: do-the-thing 1 plus-one + ;
: plus-one 1 - ;
: do-another-thing 1 plus-one + ;

do-the-thing refers to the original function, while the 2nd func do-another-thing uses the most recently defined pluse-one.
Which makes the case for replacing OPERATOR NAME with OPERATOR ARGC + OPERATOR PTR, but it is unclear how to make this work with newly defined words, which are no longer the 'operators' pre-defined via C++...

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement New feature or request
Projects
None yet
Development

No branches or pull requests

1 participant