I was doodling yesterday in meeting, and found a closed-form solution to the 2008 Ulam Spiral mini-challenge that has been haunting me for three years from: this thread.

Usage: Enter a Number (N) and execute the program. It will return the non-trivial solutions for adjacent numbers in Ulam's spiral.

For example:

17 yields 36, 38

16 yields 05, 35

14 yields 03, 33

13 yields 30, 32example spiral:

37 36 35 34 33 32 31

38 17 16 15 14 13 30

. 18 05 04 03 12 29

. 19 06 01 02 11 28

. 20 07 08 09 10 27

. 21 22 23 24 25 26

. . . . . etc..

If you're interested, I've made a Stack Diagram describing how the STAT registers and careful stack discipline can be combined to accumulate terms without local variables, and only using two numbers in the program. (integers 3 and 5)

This program has a very concise check to see if

. It returns and

for corner numbers such as 31,37,43.

Otherwise it returns and

This closed form approach allows a 30% reduction in program space, AND an order of magnitude reduction in runtime. The new program is O(1) constant runtime, 37 bytes (28 steps max for all values with no looping)- The previous version from 2008 was O(N) and 54 bytes and 43 program lines with some considerable sized loops.

' 37-byte HP 42S ULAM spiral solution Allen T. 2/5/2011

00 { 37-Byte Prgm }

01 LBL 00

02 CL\Sigma @ Clear Stat registers

03 ENTER

04 ENTER @ Fill the stack up with input

05 3

06 5

07 \Sigma+ @ add 3 and 5 to Stat regs

08 + @ add the 3 and 1 to get four

09 STOĆ ST T @ Put 4*N on level T

10 Rv @ ROLLDN

11 \Sigma+ @ Add N to each of the Stat regs

12 STO- ST Z @ Put 4N-2 on Stack level Z

13 R^ @ ROLLUP

14 +/- @ NEG

15 RCL+ ST T @ Put 4N-6 on Stack Level T

16 SQRT

17 IP

18 STO+ ST X @ find 2*floor(sqrt(4N-2)) < doubles the number in X without loosing STACK(T) 3 bytes same cost as "2 *"

19 R^

20 SQRT

21 IP

22 STO+ ST X @ find 2*floor(sqrt(4N-6))

23 X=Y? @ if the numbers are the same, then it's a SIDE

24 +/- @ Need to subtract 2* the Side number

25 ENTER

26 ABS

27 \Sigma+ @ Otherwise add 2*Side number to both stat regs

28 RCL 13 @ Recall SUM(Y) register

29 RCL 11 @ Recall SUM(X) Register

30 .END.

Thanks to Thomas for his tutorial on using formulas. I did not follow the teacher exactly, but managed to get the formulas here anyway.

* NOTE - I do not believe this program is compatible with the HP41C due to the specific use of the linear stat register and the STO/RCL arithmetic (line 15). Caveat Emptor.

Five Reasons I think this is a nice demonstration program for the 42S and RPN flexibility:

1) Lines 04 and 09 allow use of STACK(T) copies as the lower stack items are consumed in operations

2) It's one of the very few RPN programs I've seen use both ROLLUP and ROLLDN

3) Byte-saving tricks like "STO+ ST X" to double a number without disturbing the stack. (Is there a better RPN way?)

4) Uses 3 stat registers rather than local variables

5) Wherever possible uses output from the STAT accumulator instead of entering numbers (byte conservation)

*Edited: 5 Feb 2011, 11:11 p.m. *