newRPL: Named subroutines proposal
10-12-2015, 02:51 PM
Post: #1
 Claudio L. Senior Member Posts: 1,840 Joined: Dec 2013
newRPL: Named subroutines proposal
Here's another idea for open discussion:
How about having a syntax for named subroutines?
For example, it could be similar to a tagged program:

Code:
 <<       @ LOCAL SUBROUTINE DECLARATION       :ADDTWO:<< 2 + >>       @ AND HERE GOES THE MAIN PROGRAM       1234 ADDTWO >>

The syntax would be compiled in the same way as:

:myTAG:<< ... >> ---> << ... >> 'myTAG' LSTO

so it would create a local variable with the subroutine ready to be executed.
It's not revolutionary but can make code more readable.
10-12-2015, 11:30 PM (This post was last modified: 10-12-2015 11:31 PM by Helix.)
Post: #2
 Helix Member Posts: 239 Joined: Dec 2013
RE: newRPL: Named subroutines proposal
I don't like the fact that this syntax breaks the RPL logic (arguments first, followed by the function).
Furthermore, since comments will be possible in newRPL, I don't see much difference with this version of your example:

Code:
<<       @ ADDTWO SUBROUTINE       << 2 + >> 'ADDTWO' LSTO       @ MAIN PROGRAM       1234 ADDTWO >>

Jean-Charles
10-13-2015, 01:55 AM
Post: #3
 Han Senior Member Posts: 1,883 Joined: Dec 2013
RE: newRPL: Named subroutines proposal
As Helix showed, LSTO is more than sufficient without also introducing flow idiosyncrasies. Moreover, I imagine the proposed syntax would also cause conflicts with tagged objects. It would seem that each instance of an embedded tagged object used within a program would result in the unnecessary creation of a corresponding local variable that may not ever be called.

Graph 3D | QPI | SolveSys
10-13-2015, 04:09 PM
Post: #4
 Claudio L. Senior Member Posts: 1,840 Joined: Dec 2013
RE: newRPL: Named subroutines proposal
(10-12-2015 11:30 PM)Helix Wrote:  I don't like the fact that this syntax breaks the RPL logic (arguments first, followed by the function).
Furthermore, since comments will be possible in newRPL, I don't see much difference with this version of your example:

Code:
<<       @ ADDTWO SUBROUTINE       << 2 + >> 'ADDTWO' LSTO       @ MAIN PROGRAM       1234 ADDTWO >>

True, you can always add a comment and it's almost the same.

(10-13-2015 01:55 AM)Han Wrote:  As Helix showed, LSTO is more than sufficient without also introducing flow idiosyncrasies. Moreover, I imagine the proposed syntax would also cause conflicts with tagged objects. It would seem that each instance of an embedded tagged object used within a program would result in the unnecessary creation of a corresponding local variable that may not ever be called.

I didn't think much about the syntax, it could use other characters to avoid conflicts, but if the only two people who care about this project think it's not a good idea, then it probably isn't. Let's forget about this one.
10-13-2015, 09:31 PM
Post: #5
 rprosperi Super Moderator Posts: 5,254 Joined: Dec 2013
RE: newRPL: Named subroutines proposal

I think plenty of other folks care bout newRPL, so please don't take a lack of comments to mean that no one else cares.

Speaking only for myself, I think extensions to existing RPL which break the general syntax and style should only be considered if the extension adds significant functionality and/or other dramatic benefits. Without such benefits, I think most users are unlikely to even bother learning these extensions, so the effort to implement (and test!) them is likely better spent on core features. Just one opinion, others may vary.

--Bob Prosperi
10-13-2015, 11:09 PM
Post: #6
 Helix Member Posts: 239 Joined: Dec 2013
RE: newRPL: Named subroutines proposal
Here is another suggestion to make code more readable.

In RPL, code like A B SIN * C + 'Z' STO is not very clear.
There is an elegant solution, provided that the flag -3 is set:
'Z=A*SIN(B)+C' DEFINE
(I must admit that I have discovered this possibility only today!)

It would be nice to have also the command LDEFINE, which would create a local variable, in the same way as LSTO. This would make newRPL more similar to modern languages, but still following the RPL syntax. Of course, there would be a cost in speed processing, but since newRPL is much faster than RPL, it could be interesting in most cases.

Jean-Charles
10-14-2015, 04:43 PM
Post: #7
 Claudio L. Senior Member Posts: 1,840 Joined: Dec 2013
RE: newRPL: Named subroutines proposal
(10-13-2015 11:09 PM)Helix Wrote:  Here is another suggestion to make code more readable.

In RPL, code like A B SIN * C + 'Z' STO is not very clear.
There is an elegant solution, provided that the flag -3 is set:
'Z=A*SIN(B)+C' DEFINE
(I must admit that I have discovered this possibility only today!)

It would be nice to have also the command LDEFINE, which would create a local variable, in the same way as LSTO. This would make newRPL more similar to modern languages, but still following the RPL syntax. Of course, there would be a cost in speed processing, but since newRPL is much faster than RPL, it could be interesting in most cases.

DEFINE is not implemented yet, but will be implemented (but it doesn't count as an improvement to RPL, it has been there forever).
LDEFINE would be a nice addition, and it will definitely be added.

Regarding flag -3: here you have another perfect example why I dislike commands that depend on system flags. DEFINE works best when defining functions, and in that case, it works regardless of the flag, but if you define only a variable, it wants to evaluate the expression first and fails. Doesn't make much sense to me, I'd rather have DEFINE to define it as the expression and perhaps NUMDEFINE if I want to run ->NUM before.
10-14-2015, 06:52 PM (This post was last modified: 10-14-2015 06:54 PM by Han.)
Post: #8
 Han Senior Member Posts: 1,883 Joined: Dec 2013
RE: newRPL: Named subroutines proposal
(10-14-2015 04:43 PM)Claudio L. Wrote:  DEFINE is not implemented yet, but will be implemented (but it doesn't count as an improvement to RPL, it has been there forever).
LDEFINE would be a nice addition, and it will definitely be added.

Regarding flag -3: here you have another perfect example why I dislike commands that depend on system flags. DEFINE works best when defining functions, and in that case, it works regardless of the flag, but if you define only a variable, it wants to evaluate the expression first and fails. Doesn't make much sense to me, I'd rather have DEFINE to define it as the expression and perhaps NUMDEFINE if I want to run ->NUM before.

At some point we have to realize that system flags are a must. Some things are black and white so that a system flag will be either permanently set for some and cleared for others (e.g. how complex numbers are displayed -- as (a,b) or a+bi). The issue here, though, really isn't about system flags but how we want the system to handle symbolic objects. The question of whether symbols should be resolved prior to executing the command is the very issue that was a big headache even as far back as the HP48 (resolved slightly via flag -3) and is really bad in the HP Prime. Should inputs be parsed so that all symbols are resolved prior to passing to a command? Or should the command leave some/all of the symbols as they are? To suggest that we have two versions of the same command for each command that handles symbolic input would be beyond crazy, in my humble opinion. There are far to many commands as it is, even for just the HP48.

Graph 3D | QPI | SolveSys
10-15-2015, 12:07 AM (This post was last modified: 10-15-2015 12:16 AM by Helix.)
Post: #9
 Helix Member Posts: 239 Joined: Dec 2013
RE: newRPL: Named subroutines proposal
(10-14-2015 04:43 PM)Claudio L. Wrote:  DEFINE is not implemented yet, but will be implemented (but it doesn't count as an improvement to RPL, it has been there forever).

DEFINE has been there forever, but I didn't know it was possible to use this command to define a variable. I don't think it's documented in the user's guide, only in the AUR.

(10-14-2015 04:43 PM)Claudio L. Wrote:  Regarding flag -3: here you have another perfect example why I dislike commands that depend on system flags.

I have similar thoughts than Han. I don't consider flags as a drawback. If we decide to suppress flags, then we have no other choice than multiplying the number of commands, as it was discussed previously about trig functions. What is gained somewhere is lost elsewhere.

However, I can understand that in some cases avoiding flag dependence can be interesting.
I find NUMDEFINE a bit long for a command. Instead, what about ASSIGN ? There is already the command UNASSIGN that purges global variables, so ASSIGN would make sense. In the same way, LASSIGN would create local variables.

(10-14-2015 04:43 PM)Claudio L. Wrote:  DEFINE works best when defining functions, and in that case, it works regardless of the flag, but if you define only a variable, it wants to evaluate the expression first and fails.

Well, if flag -3 is set, and at least one variable in the algebraic expression doesn't exist, then DEFINE fails, but it's normal. I suppose the same thing would happen with ASSIGN (or NUMDEFINE) in such a case.

Jean-Charles
10-15-2015, 01:33 AM
Post: #10
 Claudio L. Senior Member Posts: 1,840 Joined: Dec 2013
RE: newRPL: Named subroutines proposal
(10-14-2015 06:52 PM)Han Wrote:  At some point we have to realize that system flags are a must. Some things are black and white so that a system flag will be either permanently set for some and cleared for others (e.g. how complex numbers are displayed -- as (a,b) or a+bi).

And I agree 100%. That's exactly what flags are for. To control certain behaviors and preferences from the user. But should flags be allowed to control the output of commands so extensively as they are?
The constant "suggested" mode changes are annoying, and they only exist to mitigate the frustration of users that would get either wrong results or error messages. Then the large amount of posts in the forum saying things like "I do this and I can't get an answer" and were replied with "set flags -3, -23, -57 and there you go" (flag numbers are made up, BTW).
I don't say we don't need flags, I simply think that 700 commands and 128 flags is too many, there has to be a way to simplify that.

(10-14-2015 06:52 PM)Han Wrote:  The issue here, though, really isn't about system flags but how we want the system to handle symbolic objects. The question of whether symbols should be resolved prior to executing the command is the very issue that was a big headache even as far back as the HP48 (resolved slightly via flag -3) and is really bad in the HP Prime. Should inputs be parsed so that all symbols are resolved prior to passing to a command? Or should the command leave some/all of the symbols as they are?
I think we are getting to the point. There should be a simple syntax for the user to indicate what he wants.
In newRPL, the trailing dot was used to indicate numbers that want to be operated upon immediately (which I call approximated). This could be extended to commands and variables for example, to try to do what you suggest.
For example 'SIN(X)' would only evaluate X when you EVAL the expression, not when you enter it. But perhaps you could write 'SIN(X.)' to indicate you want X replaced immediately, and you'd see on the stack 'SIN(pi/2)' assuming 'pi/2' is the contents of X, and this could be recursive, if the contents is 'pi./2' then pi would be replaced immediately.
In other words, the trailing dot would work as an abbreviation of EVAL, and you use it whenever you want in your expression.
The opposite is also possible (and perhaps more common): if you want a symbol not evaluated you use some sort of "quote" command or symbol to prevent evaluation, otherwise it gets evaluated. This is more for languages where symbolic computing is very rare, otherwise you'd have "quote" all over your expressions.

(10-14-2015 06:52 PM)Han Wrote:  To suggest that we have two versions of the same command for each command that handles symbolic input would be beyond crazy, in my humble opinion. There are far to many commands as it is, even for just the HP48.
That's of course an exaggeration, most commands can work around their flag issues, only a few would need to be split. In the case of DEFINE, for example something like the trailing dot explained above would solve the problem completely. The expression itself would ask to be evaluated or not, it is not for the command to decide.
10-15-2015, 10:07 PM
Post: #11
 Helix Member Posts: 239 Joined: Dec 2013
RE: newRPL: Named subroutines proposal
So, just to understand, what would be the syntax with my example:
'Z=A.*SIN(B.)+C.' DEFINE ?

Jean-Charles
10-16-2015, 02:19 AM
Post: #12
 Claudio L. Senior Member Posts: 1,840 Joined: Dec 2013
RE: newRPL: Named subroutines proposal
(10-15-2015 10:07 PM)Helix Wrote:  So, just to understand, what would be the syntax with my example:
'Z=A.*SIN(B.)+C.' DEFINE ?

If you want Z to have the expression: 'A+SIN(B)+C', then:
'Z=A+SIN(B)+C' DEFINE
This would work as if your flag -3 is set to symbolic.

If you want the variables to be evaluated before defining Z, then:
'Z=A.*SIN(B.)+C.'
would recall A, B and C when executed in the runstream, and have their results replaced in the expression. This happens before execution knows what command will be next.
By the time you reach DEFINE, the modified expression is in the stack, and that expression will be assigned to Z.
This works similar to when you set flag -3 to numeric, except you actually control what you want evaluated or not.
The flag can still be needed, but at the UI level. For example, we could have flag -3, but what it would do is every time you type a variable, it appends a dot, indicating you want the numeric result. In the end, it "forces" numeric results system-wide, but not because the commands are behaving different, it's because the input you are giving is different.
Ideally, a program should behave in a deterministic way, as long as you provide identical input, it should produce identical output.
For constants, the same syntax could work just as well (eliminating the need for flag -2). You type π and you get the symbolic constant π on the stack. You type π. and you get the number 3.141592.... on the stack.
10-16-2015, 07:49 AM (This post was last modified: 10-16-2015 07:51 AM by Paul Dale.)
Post: #13
 Paul Dale Senior Member Posts: 1,750 Joined: Dec 2013
RE: newRPL: Named subroutines proposal
(10-15-2015 01:33 AM)Claudio L. Wrote:  And I agree 100%. That's exactly what flags are for. To control certain behaviors and preferences from the user.

For mode settings, the 34S uses individual named commands. We also made the decision early on that these flags setting commands do not impact user flags or user visible memory. The command names are far more meaningful than the numeric flags. You've already got some commands that do exactly this (DEG/RAD/GRAD e.g.). Mirroring a command name with some numeric flags is a throwback to the 1970s or 1980s when code and RAM was extremely tight.

I would wholeheartedly recommend that you use individual meaningful command names and have them operate on hidden memory. Also provide separate interrogation commands to query the current setting and a save/restore all settings command pair.

For a quick test what does flag 14 do on the HP-41? What about flag 49? Can you think of reasonable command names to set and clear these?

For the 34S we decided early on that numeric flags were exclusively for the user & we've resisted multiple attempts to hijack these. The lettered flags were originally also for the user, excepting the B and C flags which supported integer mode's overflow (big) and carry. The D and A flags got special meaning afterwards and then the number was increased to match the registers in order to support local registers and flags. The entire reason we had alpha flags is because 0 -- 99 plus A - D comes to a whole number of bytes.

Yes, I know RPL system flags have negative numeric values and user flags are positive, but a memorable command name is still much better.

- Pauli
10-16-2015, 08:44 PM
Post: #14
 Claudio L. Senior Member Posts: 1,840 Joined: Dec 2013
RE: newRPL: Named subroutines proposal
(10-16-2015 07:49 AM)Paul Dale Wrote:  Yes, I know RPL system flags have negative numeric values and user flags are positive, but a memorable command name is still much better.

I don't think I ever mentioned this but the flag commands in newRPL support the numeric designation only for backwards compatibility, we have names for flags and/or groups of flags. So every flag will get a name:
'DEG' SF will set the angle mode in degrees, same as the DEG command. Flag query commands FS? and FC? were also extended to support named flags.
There's commands that change flags, like DEG, GRAD and RAD, but I think the named flag used with the traditional SF, CF commands is the preferred way (in my opinion), so you know you are setting a flag.
10-16-2015, 11:57 PM
Post: #15
 Paul Dale Senior Member Posts: 1,750 Joined: Dec 2013
RE: newRPL: Named subroutines proposal
That makes a lot of sense.

Pauli
10-24-2015, 12:39 PM
Post: #16
 Claudio L. Senior Member Posts: 1,840 Joined: Dec 2013
RE: newRPL: Named subroutines proposal
(10-15-2015 01:33 AM)Claudio L. Wrote:  In newRPL, the trailing dot was used to indicate numbers that want to be operated upon immediately (which I call approximated). This could be extended to commands and variables for example, to try to do what you suggest.
For example 'SIN(X)' would only evaluate X when you EVAL the expression, not when you enter it. But perhaps you could write 'SIN(X.)' to indicate you want X replaced immediately, and you'd see on the stack 'SIN(pi/2)' assuming 'pi/2' is the contents of X, and this could be recursive, if the contents is 'pi./2' then pi would be replaced immediately.