▼
Posts: 1,477
Threads: 71
Joined: Jan 2005
OK not really but close!
Although I said I was going to stop playing with this "buggy little beast" (thank you Nenad) I apparently have not.
In rereading Gene's review I was struck by the ability to store into variables within an equation and thought that I might see what could be done with this. A good exercise would be to try to fill the indirect array with data by just using the solver, then take this one step further and add a way to control the endpoints.
First we some way to keep the solver running indefinitely, this little equation works well:
1/A = 1/A
(that's a unary )
Using this, the ability to STO I, STO(I) and adding a stopping condition we get:
(IDIV(I,N)1)/A = (1IDIV(I,N))/A + 0x(I+1 > I > (I))
(Here the ">" represents the filled in ">" that you see when you
press STO in an equation.)
Enter this and press SOLVE. Solve for A, enter the starting value for I and the ending value for N and the "buggy little beast" will fill the array locations I thru N with the values I thru N! Actually because the solver wants to confirm that it found a zero (by doing an extra iteration) and because of the way I wrote the equation it will start at I+1 and fill to N+2, but you can easily make the needed adjustments.
This opens up the possibility of doing all sorts of calculations in the equation solver that would normally be done with SIGMA on a 17BII (for example), even more when you consider that you have an array that can be read/write addressed. Here's a really serious challenge: write an equation that uses the solver to calculate a few hundred digits of pi.
Edited: 12 Aug 2007, 12:43 a.m.
▼
Posts: 1,392
Threads: 142
Joined: Jun 2007
Katie, educate me here. I'm trying to better understand the internal behavior of the solver, especially the 17bii+ solver in relation to the 17bii solver, but I am intrigued by your 35s example.
How does your equation cause the solver to iterate from a specific starting point to a specific stopping point?
▼
Posts: 1,477
Threads: 71
Joined: Jan 2005
The 17BII and 17BII+ have a Sigma function in the solver that forces it to specifically iterate over a defined interval (see below for more). There is no such function in the 35s. Solver iteration in the 35s is determined by the internals of how the solver works and is generally not controllable. On the other hand, you can trick the solver into running for a really long time by giving it an equation that it can't solve yet slowly converges, something like: INV(A) = INV(A).
However, the 35s does have a STO function that seems identical to the L() function in the 17BII and 17BII+, this allows for incrementing a variable: e.g., I+1 STO I. Using these two pieces we can get the solver to run while for an incredibly long time while incrementing a variable. If you tell it to solve: INV(A) = INV(A)+ 0x(I+1 STO I), solve for A and give it a starting value of I=0 and A=1, it will run for about 2400 iterations on the 35s. after that point the solver will end up solving the equation by coming up with A ~= 1E499. 2400 is pretty much all the iterations you'd ever want to do on this calculator  it ain't that fast  I'll call it a nearinfinite number of iterations for our purpose.
Here's how the rest of it works ... if 'I' is not the target of the solver, then the solver will prompt for the starting value. That leaves just the ending value and the need to use this ending value as a way to halt the solver's nearinfinite loop. In the equation I wrote above this is done by, 1IDIV(I,N). This will have a value of 1 when 'I' is less than N and of 0 when I becomes N (and until 'I' becomes 2N). Using this on both sides of the "=' the equation becomes 0 = 0 when 'I' becomes N, thus achieving the stopping condition for the solver.
The other element in the equation is: I STO (I). This is just to demonstrate that the controlled loop can do something useful: fill addressable memory with incremental values. You could just have well specified: 0x(I+1 > I + RAND > (I)) to fill memory (from the initial value of I to N) with random numbers.
This is all pretty nonobvious stuff and I've just begun to experiment with it, but it's amazing what just the STO function in the solver opens up. You won't find anything about this in the manual (or anywhere else as fas as I know).
I don't have a 17BII+ but on the 17BII you can do the same thing in the solver: INV(A)=INV(A)+0xL(I:I+1). Start with I=0 and A=1, solver for A and RCL I when it finishes and you'll find that I has a value of about 2400, showing that this many iterations have been done. Unfortunately you can't 'STO (I)' on the 17BII because it has no way to write to an array (although you can read the items in a list from within the solver). Of course you would never really do this on the 17BII you'd use: X=Sigma(I:1:N:1,whatever you want to do). Note that 'Sigma' is the summation sign and 'whatever you want to do' will be evaluated N times and the results will be summed and returned in X.
Edited: 13 Aug 2007, 11:23 a.m.
▼
Posts: 1,392
Threads: 142
Joined: Jun 2007
Wow!
It will take me a while to digest what you said. On first reading, I think I understand most of it, but I've got some playing around to do. You have really done some good work here, and I congratulate you.
I wish there was a book called "Everything you always wanted to know about the inner workings of the solver, but were afraid to ask." I'm still trying to figure out why the 17bii+ solver does not work like the 17bii solver (and it doesn't, believe me, especially with the sigma function).
Thanks Katie.
Posts: 735
Threads: 34
Joined: May 2007
Quote:
Here's a really serious challenge: write an equation that uses the solver to calculate a few hundred digits of pi.
When I first realized that we have about 800 registers to waste I
was thinking what could I do that wasn't possible with my HP11c?
Now with your challenge in mind I transcribed a Cprogram which uses
the spigot algorithm for the digits of pi:
P001 LBL P P018 FS? 0 P035 INT/
P002 STO N P019 GTO P022 P036 DSE J
P003 4 P020 RCL(J) P037 GTO P017
P004 INT/ P021 GTO P023 P038 ENTER
P005 STO I P022 2E3 P039 CF 0
P006 CLx P023 RCL* F P040 RCL F
P007 STO D P024 + P041 INT/
P008 STO E P025 1 P042 RCL+ E
P009 1E4 P026 RCL J P043 STO P
P010 STO F P027 ENTER P044 VIEW P
P011 SF 0 P028 + P045 x<>y
P012 14 P029 x<>y P046 RCL F
P013 RCL* I P030  P047 RMDR
P014 STO J P031 RMDR P048 STO D
P015 DSE J P032 STO(J) P049 STO E
P016 RCL D P033 x<>y P050 DSE I
P017 RCL* J P034 LASTx P051 GTO P012
40 XEQ P001
P=
3141
5926
5358
9793
2384
6264
3383
2795
288 <<< mind the missing 0
4197
Though untested it should be possible to calculate a little more than the the first 200 digits. Using vectors could lead to even more digits.
But when I tried to write an equation for that algorithm I wondered
how should I handle the inner and the outer loop? We can't use the
solver within the solver, do we?
Probably I have to use a different approach then.
The Cprogram was taken from:
Pi Unleashed.
Jörg Arndt, Christoph Hänel
▼
Posts: 1,477
Threads: 71
Joined: Jan 2005
That's a pretty neat algorithm for pi and fits in a limited program space, nice work!
Like you mention it's at the expense of variable space and (I think) there's a risk of not working if there is a 99999... sequence somewhere in the first so many digits of pi that the program generates. (I know that the original Rabinowitz and Wagon program had this problem.)
However, the convergence is pretty fast and this might fit more easily into an solver equation than some more conventional methods. It's possible to simulate nested loops in the solver by doing something like:
(1IDIV(C,N^2))*INV(A)=(IDIV(C,N^2)1)*INV(A)
+ 0*
(C+1 STO C +
IDIV(C,N) STO I +
RMDR(C,N) STO J +
....
I and J could now be used as row/column indicies into a matrix (if only the 35s had matrices) or whatever.
I haven't yet tried to write an equation to solve for pi in the 35s solver, but some time ago I did it in the solver in the HP 200LX using a similar technique and storing/reading values from an list in the builtin Lotus 123 application. Look at the end of
this thread to see how complicated it is. Without a better equation editor in the 35s I wouldn't want to try using this technique.
Katie
Edited: 15 Aug 2007, 3:45 a.m.
▼
Posts: 1,153
Threads: 94
Joined: Mar 2006
. . . what further enhancements you might suggest to solidify and/or expand this newfound usefulness of the 35s' SOLVE?
(I must admit I don't fully appreciate what this is all about. But I suspect that any feature which elicits such a positive response from K.W. deserves the full attention of the calculator cadre at HP!)
Edited: 15 Aug 2007, 5:35 p.m.
▼
Posts: 1,477
Threads: 71
Joined: Jan 2005
Paul,
I'm flattered by your comment but have to admit that this "hidden" solver functionality just adds up to little more than a curiosity. Because you can use the solver on a program, there's nothing that you can do within an equation that you can't do pragmatically; programs are also faster, more readable and more easily changed.
The only somewhat useful things I can think of given the ability to use STO in an equation are:
(1) It provides a shortcut to retyping an subexpression (not involving the target variable) that appears more than once in an equation.
(2) You can store intermediate results and view these after the solver finishes. This might allow you study how your equation converges, see how errors accumulate or save sideeffect results in a calculation.
(3) Using a simple counter (C+1 STO C) allows you to determine the number of iterations the solver takes.
Of course all of the above are really just shortcuts, nothing that can't be programed.
Katie
▼
Posts: 1,153
Threads: 94
Joined: Mar 2006
Thank you for your thoughtful inclusion of a clear explanation.
I wonder whether HP might be interested in including the feature (and maybe more straightforward nested looping) in all of their SOLVEcapable machines. Then, even the ones that aren't strictly "programmable" might have greater capability than they might have otherwise.
Edited: 16 Aug 2007, 4:15 p.m.
Posts: 217
Threads: 21
Joined: Aug 2007
Quote:
(1) It provides a shortcut to retyping an subexpression (not involving the target variable) that appears more than once in an equation.
That strikes me as dangerous. How can you know that the instance of the subexpression that does the STO gets executed before you use the STO'd value? Is there any guarantee that it executes from left to right?
Stefan
▼
Posts: 2,448
Threads: 90
Joined: Jul 2005
In the 17b/19b/27s family, the direction of execution is spelled out clearly and the functions (L)et and (G)et are provided for this purpose. Katie is merely applying the same principle to the 35sand it should be checked out but it just may work the same!
▼
Posts: 1,477
Threads: 71
Joined: Jan 2005
You're correct. Since the STO function is not documented there is now way to know for sure where it stands in order of precedence, nor even if it has the same precedence in all situations. My simple trial evaluations show that it has the lowest level of precedence and works lefttoright. But there's certainly no guarantee of this and it should be used with great caution.
(To take caution a step further, and given the checksum bug, it's even possible that STO might get different results each time the function is evaluated depending on the state of the machine.)
Posts: 735
Threads: 34
Joined: May 2007
After playing a little more with the solver I realized that SGN could be used as well to count down.
Due to the lack of a conditional branch within the solver I wanted to use two equations.
First initialize the elements of the array to 2000 and then perform the inner loop.
Initalize registers I ... 0 to 2000:
0*(2000>(I))+SGN(I1>I)/A+SGN(I)/A
Calculation of the inner loop:
0*(I+I1>G)*
(RMDR(D*I+(I)*1E4>D,G)>(I))*
(IDIV(D,G)>D)
+SGN(I1>I1)/A+SGN(I1)/A
But alas the result was wrong!
It was only after a longer debugging session when I realized that RCL (I) doesn't behave as I had expected.
The following equation may be used for some tests:
0*(S+(I)>S)+SGN(I1>I)/A+SGN(I)/A
Solve for A, set S=0 and I=10 and see what happens.
You might expect to find in S the sum of the values of the registers 0  10 but instead you get 11 times the value of register 10.
It seems that when recalling an indirect register from within an equation the index isn't updated for each iteration. Instead (I) refers always to the same register.
However when storing a value into an indirect register the solver behaves as expected. That's why the initialization with 2000 works fine.
You may call it a bug. On the other hand why would somebody want to do such a strange thing?
With this behavior of the solver I suspect it's quiet impossible to calculate a few hundred digits of pi. Or maybe it's only now that I realize the real dimension of your challenge.
▼
Posts: 1,477
Threads: 71
Joined: Jan 2005
Thomas,
You reached the same conclusion as I did after some further experiments  recalling (I) or (J) is not predicable in the solver. When I suggested the "pi challenge" I wasn't sure if this problem could be overcome or not, but since then I haven't found a way around it. [I was getting very frustrated trying to write a sort function in the solver.] But there might be some hidden function like the G() function in the 17Bii solver that no one has found yet.
Gene, how did you know about the STO function, inside knowledge or did you just stumble upon it?
Katie
▼
Posts: 55
Threads: 5
Joined: Jul 2007
Quote:
But there might be some hidden function like the G() function in the 17Bii solver that no one has found yet.
In the beginning (before reading the manual :), I didn't know how to enter the REGX, REGY, functions, so I tried RCL R, RCL E, RCL G, RCL X. And it worked. Same thing for example for SIN(X): instead of the easy way: SIN RCL X, use RCL S, RCL I, RCL N, (), RCL X. It works.
In other words, it seems EQN actually parses the command line edited under EQN mode. Maybe there are some hidden functions in there, for which there is no keyboard shortcut?
*edit*: I just tried G(REGX), and it didn't give me the usual SYNTAX ERROR!
*edit 2*: It seems A(REGX) is equivalent to RCL A *
Edited: 21 Aug 2007, 1:36 a.m.
▼
Posts: 1,477
Threads: 71
Joined: Jan 2005
G(X) is just an implied multiply of G times X in the 35s solver.
RCL whatever is simply the way to enter any variable in the solver.
The get, G(), function I was referring to is a special function in the 17bii solver (and several other HP calculators going back to the 27S) that recalls the value of a variable each time it's encountered. When used in combination with the let, L(), function it allows for sideeffects in the solver. The 35s solver apparently has the L() function (in the form of STO) but not the G() function, or so it seems.
Posts: 1,545
Threads: 168
Joined: Jul 2005
I did not stumble upon it.
