(08-04-2022, 10:37 PM)Jack Wrote: Pete said " I've used this statement for years for a variety of things but was not aware of the optional indexing. Always nice to learn something along the way"
you can also use the Asc statement like this
a$="123"
Asc(a$, 1) = 48
Print a$ '--> 023
not sure that Asc was designed to function that way however, it could be a "feature"
just for fun I replaced Val with Asc where possible in the Treebeard's string-math and the multiply was 14 times faster, division was 40% faster
Huh? I must be going in the WRONG direction, because I just figured out a way to make mine 14 times slower!
How to handle really big numbers using STRING VAL()
Code: (Select All)
CLS
WIDTH 160, 25
_SCREENMOVE 0, 0
neg_a = 0: neg_b = 0: dec_a1$ = "": dec_a2$ = "": dec_b1$ = "": dec_b2$ = ""
LINE INPUT "First number a: "; a$
LINE INPUT "Second number b: "; b$
IF b$ = "" THEN ' Demo if nothing input.
a$ = "11" + STRING$(50000, "0") + "1.001"
b$ = "11" + STRING$(50000, "0") + "1.002"
END IF
REM Remove trailing zeros after a decimal point.
IF INSTR(a$, ".") THEN
DO UNTIL RIGHT$(a$, 1) <> "0" AND RIGHT$(a$, 1) <> "." AND RIGHT$(a$, 1) <> "-"
a$ = MID$(a$, 1, LEN(a$) - 1)
LOOP
END IF
IF INSTR(b$, ".") THEN
DO UNTIL RIGHT$(b$, 1) <> "0" AND RIGHT$(b$, 1) <> "." AND RIGHT$(b$, 1) <> "-"
b$ = MID$(b$, 1, LEN(b$) - 1)
LOOP
END IF
IF MID$(a$, 1, 2) = "-0" OR a$ = "" OR a$ = "-" THEN a$ = "0"
IF MID$(b$, 1, 2) = "-0" OR b$ = "" OR b$ = "-" THEN b$ = "0"
IF MID$(a$, 1, 1) = "-" THEN neg_a = -1
IF MID$(b$, 1, 1) = "-" THEN neg_b = -1
IF INSTR(a$, ".") THEN
dec_a1$ = MID$(a$, 1, INSTR(a$, ".") - 1): dec_a2$ = MID$(a$, INSTR(a$, ".") + 1)
ELSE
dec_a1$ = a$
END IF
IF INSTR(b$, ".") THEN
dec_b1$ = MID$(b$, 1, INSTR(b$, ".") - 1): dec_b2$ = MID$(b$, INSTR(b$, ".") + 1)
ELSE
dec_b1$ = b$
END IF
DO
' Test for sign.
SELECT CASE neg_a + neg_b
CASE 0, -2 ' Both positive or negative
IF dec_a1$ = dec_b1$ AND dec_a2$ = dec_b2$ THEN a_less_b = 0: EXIT DO ' Same number.
IF LEN(dec_a1$) AND dec_b1$ = "" THEN a_less_b = 1: EXIT DO ' a >=1 and b is a decimal.
IF LEN(dec_b1$) AND dec_a1$ = "" THEN a_less_b = -1: EXIT DO ' b >=1 and a is a decimal.
IF LEN(dec_a1$) AND dec_a1$ <> dec_b1$ OR LEN(dec_b1$) AND dec_a1$ <> dec_b1$ THEN ' One or both >=1 and non-decimal parts are not equal.
IF LEN(dec_a1$) > LEN(dec_b1$) THEN a_less_b = 1: EXIT DO
IF LEN(dec_a1$) < LEN(dec_b1$) THEN a_less_b = -1: EXIT DO
IF LEN(dec_a1$) = LEN(dec_b1$) THEN
FOR i = 1 TO LEN(dec_a1$)
IF MID$(dec_a1$, i, 1) <> MID$(dec_b1$, i, 1) THEN EXIT FOR
NEXT
IF MID$(dec_a1$, i, 1) < MID$(dec_b1$, i, 1) THEN a_less_b = -1: EXIT DO ELSE a_less_b = 1: EXIT DO
END IF
ELSE ' Both decimals or non-decimal digits are the same and cancel out.
j = LEN(dec_a2$)
IF LEN(dec_b2$) > j THEN j = LEN(dec_b2$)
FOR i = i TO j
IF MID$(dec_a2$, i, 1) <> MID$(dec_b2$, i, 1) THEN EXIT FOR
NEXT
IF MID$(dec_a2$, i, 1) < MID$(dec_b2$, i, 1) THEN a_less_b = -1: EXIT DO ELSE a_less_b = 1: EXIT DO
END IF
CASE -1 ' One is negative.
j = -999
IF neg_a THEN a_less_b = -1: EXIT DO ELSE a_less_b = 1: EXIT DO
END SELECT
EXIT DO
LOOP
IF neg_a OR neg_b THEN IF j <> -999 THEN a_less_b = a_less_b * -1
PRINT: IF LEN(a$) < 60 AND LEN(b$) < 60 THEN PRINT a$; " "; b$, ELSE PRINT "Number(s) too big to print to line.",
IF a_less_b < 0 THEN PRINT "a$ < b$" ELSE IF a_less_b = 0 THEN PRINT "a$ = b$" ELSE PRINT "b$ < a$"
REM PRINT dec_a1$, dec_a2$, dec_b1$, dec_b2$, neg_a, neg_b
PRINT
SLEEP
RUN
For super large numbers these two comparison standards are unreliable...
' String comparison fails.
PRINT "a$ < b$ "; a$ < b$
PRINT "a$ = b$ "; a$ = b$
PRINT "a$ > b$ "; a$ > b$
' Value comparison fails.
PRINT "VAL(a$) < VAL(b$) "; VAL(a$) < VAL(b$)
PRINT "VAL(a$) = VAL(b$) "; VAL(a$) = VAL(b$)
PRINT "VAL(a$) > VAL(b$) "; VAL(a$) > VAL(b$)
Pete