Posts: 805
Threads: 135
Joined: Apr 2009
Reputation:
5
I was playing with some complex code from the "One Liners" stuff. The following program behaves completely differently in basic as opposed to going through the compiler. Actually, it crashes when run compiled. (I tried several different types for f and g). Oddly, at the first PLOT, there appears some other changes to the screen - a few bytes of corruption. Something weird is happening there. There are more brackets than I need - mostly in an attempt to make sure the math functions are coming out clearly. Try it in BASIN and then compile it.
I know the functions are unnecessarily complex. That's the nature of the one liner type code. Nonetheless, it ought to behave when compiled just like the interpreted version. Shouldn't it?
Code: DIM f,g as UBYTE
1 PRINT AT 9,9;"SIMON"
3 FOR f=1 TO 4
4 INK f
5 FOR g=1 TO 32
6 PLOT INT ABS((SGN (f-2.5)*80)+24+g), INT (((CODE "0202"(f TO f)-49)*99)-48+g)
7 DRAW 32,0
8 NEXT g
9 goto 11
10 STOP
11 PRINT INK f; OVER 1;AT CODE "1919"(f TO f)-44,CODE "0099"(f to f)-41;f
12 NEXT f
13 LET f=1
14 goto 9
Posts: 1,763
Threads: 55
Joined: Aug 2019
Reputation:
24
The bug seems to be related CODE "0202"(f TO f) part.
The CODE <constant string> is wrong. I'm fixing it. And should also allow CODE "0202"(f) ... syntax
Meanwhile, try this workaround and see if you notice any other issue:
and use CODE z$(f) instead of CODE "0202" (the same applies for "0099", by the way)
Posts: 1,763
Threads: 55
Joined: Aug 2019
Reputation:
24
Well, I have fixed the "0909"(F to F) problem. It works now.
Regarding your program, I've managed to work, making this changes: - "0909"(F to F) can now be written as "0909"(F) (By the way, BASIN v15 does not accept this syntax, whilst Sinclair's BASIC does)
- Y coordinate for PLOT in Line 6 in your code lacks an ABS (it takes negative values). Surprisingly, Sinclair BASIC accepts negative values for PLOT if they are within range. So PLOT -1, -2 is right!. ZX Basic will do either, but will plot in a different position. Better use ABS for Y coordinate too.
- PLOT, DRAW, and CIRCLE takes the entire screen, this means they work in the vertical range 0..192. And the result will be "shifted" down 16 pixels. So PLOT x, y in Sinclair BASIC should be PLOT x, y + 16 in ZX BASIC if you want exactly the same picture (otherwise, it doesn't matter). In this case, if you don't plot at y+16, the numbers printed will be out of the drawings.
- For the strings, the index starts in 0, not in 1. So the "0909"(1) returns "9", not "0". Better use "-0909"(F) or "0909"(F - 1). The former is preferred, faster and takes less memory. The 1st character is dummy (ignored).
- The biggest problem: You're having Overflows in the coordinates calculations. CODE "a" returns an unsigned byte, but you multiply, add, etc... and get values outside the range 0..255. Better make a typecast to a wider data type, like Integer: CAST(INTEGER, CODE "-0909"(f)) should do the trick.
Here you are the modified listing:
Code: DIM f,g as UBYTE
1 PRINT AT 9,9;"SIMON"
3 FOR f=1 TO 4
4 INK f
5 FOR g=1 TO 32
6 PLOT INT ABS((SGN (f-2.5)*CAST(INTEGER, 80))+24+g), 16 + INT ABS (((CAST(INTEGER, CODE "-0202"(f))-49)*99)-48+g)
7 DRAW 32,0
8 NEXT g
9 goto 11
10 STOP
11 PRINT INK f; OVER 1;AT CODE "-1919"(f)-44,CODE "-0099"(f)-41;f
12 NEXT f
13 LET f=1
goto 4
The mayor change is Line 6 (Notice 16 + INT ABS in y coord). The program crash was due to bug in version <1.1.9 (now available for download). Also notice the "-" char before every string, and notice that (f TO f) becomes (f) for better legibility.
|