Some questions and answers about doing math in UXN
--------------------------------------------------
Q: How can I handle negative integers in UXN?
A: Uxn doesn't have any built-in support for signed integers. However, you can
emulate signed numbers using unsigned numbers by treating some of the values
as having different (negative) values from their unsigned values.
For example, treating unsigned bytes as signed results in the following:
unsigned unsigned signed
hex decimal decimal
#00 0 0
#01 1 1
#02 2 2
... ... ...
#7e 126 126
#7f 127 127
#80 128 -128
#81 129 -127
#82 130 -126
... ... ...
#fd 253 -3
#fe 254 -2
#ff 255 -1
The first 128 integers (0-127) are represented the same as unsigned and signed,
but the latter 128 are different. The basic idea here is that for values
greater than #7f (127) we subtract 256 to get their "signed value":
signed(n) = if n > 127 then n else n - 256
It turns out that many unsigned operations "work" even when treating the values
as signed. (In other words, you get the same result as you would have using a
language with signed integer types.) The following arithmetic instructions work
correctly with "signed" values:
EQU and NEQ
ADD (example: `#13 #ff ADD` returns #12)
SUB (exampel: `#02 #03 SUB` returns #ff)
MUL (example: `#02 #ff MUL` returns #fe)
Other instructions will not handle "negative" integers correctly:
GTH and LTH:
1. these work correctly when comparing values with the same sign
(example: `#80 #ff LTH` returns #01)
2. however, LTH will consider negative values greater than non-negative
values, which is incorrect.
(example: `#ff #00 GTH` returns #01, but -1 is less than 0)
These implementations will safely compare "signed" bytes:
@signed-lth ( x^ y^ -- x