最近手痒,用QBasic写了个字符环境下的汉诺塔的演示程序,比较简单,但自我感觉良好。QB64下编译通过。
'By Chen xunxun 2014.11.11
DECLARE SUB delay (tt AS SINGLE)
DECLARE SUB drawtower ()
DECLARE SUB hanoi (n AS INTEGER, a AS INTEGER, b AS INTEGER, c AS INTEGER)
DECLARE SUB move (a AS INTEGER, c AS INTEGER)
DECLARE SUB drwatower
DIM SHARED n AS INTEGER
DIM SHARED ts AS SINGLE
CLS
DO WHILE n < 1 OR n > 10
INPUT "Please input tower levels(1-10):", n
LOOP
DIM SHARED t(3, n) AS INTEGER
ts = 1 / n / n
IF ts > .5 THEN ts = .5
'set plates to No.1 tower
FOR i = 1 TO n
t(1, i) = i
NEXT i
CALL drawtower
CALL delay(1)
CALL hanoi(n, 1, 2, 3)
PRINT
PRINT
PRINT "Press any key to return."
PRINT " by CXX"
SLEEP
END
SUB delay (tt AS SINGLE)
ss = TIMER
IF tt > 0.05 THEN
DO UNTIL TIMER - ss > tt
LOOP
ELSE
FOR i = 1 TO 200000 / tt
j = j + 1
j = j - 1
NEXT i
END IF
END SUB
SUB drawtower
CLS
PRINT
PRINT
FOR i = 0 TO n
FOR j = 1 TO 3
PRINT SPC(n - t(j, i));
IF t(j, i) > 0 THEN
PRINT CHR$(218);
PRINT STRING$(t(j, i) - 1, CHR$(196));
END IF
IF i = 0 THEN
IF t(j, i) > 0 THEN
PRINT CHR$(196);
ELSE
PRINT " ";
END IF
ELSE
IF t(j, i) > 0 THEN
PRINT CHR$(197);
ELSE
PRINT CHR$(179);
END IF
END IF
IF t(j, i) > 0 THEN
PRINT STRING$(t(j, i) - 1, CHR$(196));
PRINT CHR$(191);
END IF
PRINT SPC(n - t(j, i));
PRINT " ";
NEXT j
PRINT
NEXT i
END SUB
SUB hanoi (n AS INTEGER, a AS INTEGER, b AS INTEGER, c AS INTEGER)
'move n plates from a to c via b
IF n > 1 THEN
CALL hanoi(n - 1, a, c, b)
CALL move(a, c)
CALL hanoi(n - 1, b, a, c)
ELSE
CALL move(a, c)
END IF
END SUB
SUB move (a AS INTEGER, c AS INTEGER)
'search the plate to move
ks = 0
bh = 0
js = 0
FOR i = 1 TO n
IF t(a, i) > 0 THEN
ks = i
bh = t(a, i)
'move top plate on a to new position on c
FOR j = n TO 1 STEP -1
IF t(c, j) = 0 THEN
js = j
EXIT FOR
END IF
NEXT j
EXIT FOR
END IF
NEXT i
'animating
'plate going up on a
FOR i = ks TO 1 STEP -1
t(a, i - 1) = t(a, i)
t(a, i) = 0
CALL drawtower
CALL delay(ts)
NEXT i
'plate horizon moving
pz$ = ""
FOR i = 1 TO 2 * n + 1
pz$ = pz$ + CHR$(SCREEN(3, (a - 1) * (2 * n + 2) + i))
NEXT i
IF c > a THEN
FOR i = (2 * n + 2) * (a - 1) + 1 TO (2 * n + 2) * (c - 1)
LOCATE 3, i
PRINT SPC(n * 2 + 1);
LOCATE 3, i + 1
PRINT pz$;
CALL delay(ts)
NEXT i
ELSE
FOR i = (2 * n + 2) * (a - 1) + 1 TO (2 * n + 2) * (c - 1) + 2 STEP -1
LOCATE 3, i
PRINT SPC(n * 2 + 1);
LOCATE 3, i - 1
PRINT pz$;
CALL delay(ts)
NEXT i
END IF
t(a, 0) = 0
'plating going down on c
t(c, 0) = bh
FOR i = 0 TO js - 1
t(c, i + 1) = t(c, i)
t(c, i) = 0
CALL drawtower
CALL delay(ts)
NEXT i
END SUB