Thursday, December 5, 2019

Interesting GRID Algorithm - PC/370-SQR-Excel Solutions

Previous Game Algorithm - SQR, WinBatch & PC/370 versions:
https://tdxbits.blogspot.com/2019/11/acsl-agram-card-game-exercise-just-for.html
https://tdxbits.blogspot.com/2019/11/acsl-agram-card-game-pc370-version.html
https://tdxbits.blogspot.com/2019/11/acsl-agram-pc370-keyboard-input.html

One of my personal "features" is a form of OCD (Obsessive Compulsive Disorder). I admit my symptoms of OCD can often be quirky in nature & provide no value whatsoever. A useless example would be when I have an itch on my left arm -- I scratch it -- then scratch the right side. No reason... I just do it - I have to do it. Absurd.

But other forms of OCD can be a valuable asset - especially for an Application Developer. Every line of code I write must be properly constructed, indented & commented. Even a slight typo drives me nuts & compels me to correct it. There's one typo exception I didn't correct - which is the incorrect spelling of "translater" on my PC/370 Object Code Translator demo. Creating a complex application with object code, SVC/DOS Interrupt mapping & tedious formatting punctuated with a glaring Dum-Dum typo on the main screen seemed ironic in a comedic sense - so I left it.

Another of my OCD "quirks" is automating various procedures - mundane tasks, repetitive functions, useful utilities & just plain interesting concepts - for fun. Similar to my daughter's computer lab assignment for the AGRAM card game (links above).


I bumped into an interesting Sequence Guessing Game presented on a blog by Gaetano Causio.
A cascading series of numbers with a distinct pattern for every cell. Once I solved the puzzle I had to code the algorithm.  Below you'll find versions in PC/370, SQR and Excel Formulas.

ABOVE: The original puzzle from Gaetano's blog. You should give it a try...

Before proceeding any further you should visit Gaetano's site & give the puzzle a try. He also provides the solution as well as the meaning behind the algorithm. CLICK HERE

Welcome back! I hope you were able to solve the puzzle... now for the solution & some coding:

I was able to solve the puzzle fairly quick - within 10 minutes (maybe 5) - honest - but I may have gotten lucky. I noticed several obvious patterns - the diagonal 1's - diagonal 2,4,6,8 - binary factors in the right column. Seemed coincidental. So my focus turned to the inner cells where 24 caught my eye - along with the 6 & 12 above it. Doubling the 6 was somewhat random but that's how the mind works - it produced a result of 24. I shifted a cell & found the pattern also worked for the 8 (1*2 + 6). Visually it appears the limits of the algorithm had been reached - there was no cell above the 1. But conceptually there is - nothing on top PLUS 1 to the right yields 1. The pattern is true. Then moving to the 16 - there is an 8 on top but nothing to the right - 8*2 + nothing yields 16. If you treat all whitespace as zero the formula works perfectly for rows 2 thru infinity - the first cell in the first row has a hard-coded seed value of 1.

One thing I didn't realize was the correlation between the formula and dimensions  - 1D (point), 2D (line), 3D (plane), 4D (cube), 5D (cube within a cube), etc. Gaetano provides an explanation of that aspect. Pretty cool stuff...

I'm going to start with the Excel solution since it's easy to replicate & provides the perfect visualization of a grid. Also I'm flipping the slope so it cascades to the right instead of the left therefore flipping the orientation of the adjacent component of the formula - from right to left. This makes coding easier as demonstrated by the Excel example.

Excel Solution:

Column A will represent the "nothing" values on the edge of the grid. Column B is where the values start & spread out towards the right with each row.

Cell B1 contains the value 1 - That is our starting seed.

Place the following formula in Cell B2: =B1*2+A1 (Double the overhead cell PLUS it's left adjacent cell). Replicate (copy/paste) the formula across every cell on the row (thru Z). Then Copy/Paste all cells on row 2 thru row 25. The formula changes relative to each cell - for example, the whitespace cell D2 has the formula =D1*2+C1 - which yields nothing. Perfect. 

ABOVE: Excel Solution - All cells from B2 thru Z26 are formula driven (including whitespace).

PC/370 Version:

I'll replicate the formula in PC/370 using a 15 row by 16 column grid - with each cell defined as PL8'0'. That's 240 cells initialized to zero or 240PL8'0'.

***********************************************************************
*        GRID DEFINITION                                              *
***********************************************************************
GRID     DS    0F                            FULLWORD ALIGNMENT
         DC    240PL8'0'                     GRID - 15 ROWS X 16 COLS
GRIDX    DC    XL1'FF'                       END OF GRID
***********************************************************************


ABOVE: 15 Row x 16 Column Grid - all cells initialized to zero.

The first cell in each row is set to zero & acts like the A column in the Excel example (it just provides a zero or nothing value for the formula). The next position holds the seed value of 1 - that's relative position GRID+8(8) - which translates to B1 in Excel.


         ZAP   GRID+8(8),=PL1'1'             SET SEED NUMBER 1
*
         LA    4,GRID+16*8                   LOAD ROW 2 ADDRESS
LOOP1    EQU   *
         CLI   0(4),X'FF'                    END OF TABLE??
         BE    LOOP1X                        YES - EXIT LOOP PLEASE
*
         LA    4,8(,4)                       BYPASS FIRST COLUMN
         LA    3,15                          SET COLUMN COUNT
LOOP2    EQU   *
         LR    5,4                           LOAD CELL ADDRESS
         S     5,=A(17*8)                    BUMP TO TOP/LEFT CELL
         ZAP   0(8,4),8(8,5)                 LOAD OVERHEAD CELL
         MP    0(8,4),=PL1'2'                MULTIPLY BY 2
         AP    0(8,4),0(8,5)                 ADD ADJACENT CELL
         LA    4,8(,4)                       BUMP CURRENT CELL
         BCT   3,LOOP2                       CALCULATE NEXT CELL
LOOP2X   EQU   *
         B     LOOP1                         READ NEXT ROW
LOOP1X   EQU   *


ABOVE: Populating the Grid using the algorithm -  Overhead Cell*2 Plus Top Left Cell.

Register 4 points to the current cell 0(8,4) while register 5 is set to the overhead cells (17 cells away). Specifically, 0(8,5) is the overhead adjacent left cell and 8(8,5) is the overhead cell. ZAP, MP and AP then move on to the next cell.

The output routine simply loops through the GRID again & places the cell values on the print line (using ED without a significant digit in the pattern). See SQR Output below.

SQR Version:

In the SQR version I create a 16 x 16 array - with index row 0 unused (for clarity) & column 0 used to hold the nothing (zero) values for the left edge formulas. Then loop through rows 2 thru 15 to populate the array.

!  CALCULATE CELL VALUES

create-array name=GRID size=16 field=CELL:number:16=0

let #MAXrow           = 15
let #MAXcol           = 15

let GRID.CELL (1,1)   = 1

let #row              = 2

while #row           <= #MAXrow

   let #col           = 1

   while #col        <= #MAXcol

      let #valTOP     = GRID.CELL (#row - 1, #col)
      let #valADJ     = GRID.CELL (#row - 1, #col - 1)

      let #valCELL    = #valTOP * 2 + #valADJ

      let GRID.CELL (#row, #col) = #valCELL

      let #col        = #col + 1

   end-while  

   let #row           = #row + 1

end-while



Printing results on a report:

!  PRINT RESULTS

let #row              = 1

while #row           <= #MAXrow

   print ' '                          ( +1,  1,  0 )

   let #col           = 1

   while #col        <= #MAXcol

      let #valCELL    = GRID.CELL (#row, #col)

      if  #valCELL    > 0

          print #valCELL             (  0, +2,  0 ) edit 999999999

      end-if

      let #col        = #col + 1

   end-while

   let #row           = #row + 1

end-while



Output of SQR version (same as Excel & PC/370):

ABOVE: Portion of the GRID output.

That pretty much covers everything... a fun exercise. Creating this blog post took more time than it did to solve the puzzle and create the Excel, SQR & PC/370 versions of the solution.