
                   FANCY INPUT
  The typical INPUT statement looks like this:
10 INPUT "WHAT IS YOUR NAME";N$
It makes the computer ask ``WHAT IS YOUR NAME?'' then wait for 
you to answer to question. So when you run the program, the 
conversation looks like this:
WHAT IS YOUR NAME? MARIA
  Notice that the computer automatically adds a question mark at 
the end of the question, and leaves a blank space after the 
question mark.

           Omitting the question mark
  If you want to omit the question mark and the blank space, 
replace the semicolon by a comma:
10 INPUT "WHAT IS YOUR NAME",N$
The computer will omit the question mark and the blank space, so 
the conversation will look like this:
WHAT IS YOUR NAMEMARIA
  Here's a prettier example of how to use the comma:
10 INPUT "PLEASE TYPE YOUR NAME...",N$
The conversation will look like this:
PLEASE TYPE YOUR NAME...MARIA
  Here's an even prettier example:
10 INPUT "TO BECOME A MOVIE STAR, TYPE YOUR NAME NEXT TO THE 
STARS***";N$
The conversation will look like this:
TO BECOME A MOVIE STAR, TYPE YOUR NAME NEXT TO THE STARS***MARIA

               Omitting the prompt
  The typical INPUT statement contains a question, such as ``WHAT 
IS YOUR NAME''. The question is called the prompt. If you wish, 
you can omit the prompt, like this:
10 INPUT N$
That line doesn't include a question, but the computer still 
prints a question mark followed by a blank space, so the 
conversation looks like this:
? MARIA
  To make that example more practical, add a PRINT statement 
above line 10, like this:
9 PRINT "PLEASE TYPE YOUR NAME AFTER THE QUESTION MARK"
10 INPUT N$
That makes the conversation look like this:
PLEASE TYPE YOUR NAME AFTER THE QUESTION MARK
? MARIA


          Adjacent printing
  Here's a simple program:
10 INPUT "WHAT IS YOUR NAME";N$
20 PRINT "!!!WHAT A WONDERFUL NAME!!!"
It produces this conversation:
WHAT IS YOUR NAME? MARIA
!!!WHAT A WONDERFUL NAME!!!
  To have more fun, insert a semicolon immediately after the word 
INPUT, like this:
10 INPUT;"WHAT IS YOUR NAME";N$
20 PRINT "!!!WHAT A WONDERFUL NAME!!!"
The conversation will begin normally:
WHAT IS YOUR NAME? MARIA
But when you press the ENTER key after MARY, the extra semicolon 
makes the computer print line 20 next to MARIA, like this:
WHAT IS YOUR NAME? MARIA!!!WHAT A WONDERFUL NAME!!!
  To surprise your friends, run this program:
10 INPUT;"WHAT IS YOUR NAME";N$
20 PRINT N$;N$;N$
The program begins by asking:
WHAT IS YOUR NAME?
Suppose the person says MARIA, like this:
WHAT IS YOUR NAME? MARIA
When the person presses the ENTER key after MARIA, line 20 
automatically prints MARIA three more times afterwards, like 
this:
WHAT IS YOUR NAME? MARIAMARIAMARIAMARIA
  This program asks for your first name, then your last name:
10 INPUT;"WHAT IS YOUR FIRST NAME";F$
20 INPUT "   WHAT IS YOUR LAST NAME";L$
Line 10 makes the conversation begin like this:
WHAT IS YOUR FIRST NAME? MARIA
When you press the ENTER key after MARIA, the extra semicolon in 
line 10 makes line 20 appear on the same line, like this:
WHAT IS YOUR FIRST NAME? MARIA   WHAT IS YOUR LAST NAME?
If you answer WONG, the whole conversation looks like this:
WHAT IS YOUR FIRST NAME? MARIA   WHAT IS YOUR LAST NAME? YEE

           Multiple input
  This program asks for your name, age, and weight:
10 INPUT "NAME, AGE, WEIGHT";N$,A,W
  When you run the program, the computer asks:
NAME, AGE, WEIGHT?
  The computer waits for you to type your name, age, and weight. 
When you type them, put commas between them, like this:
NAME, AGE, WEIGHT? JOHN,25,148
  If your name is ``JOHN SMITH, JR.'', and you want to input all 
that instead of just JOHN, you must put quotation marks around 
your name:
NAME, AGE, WEIGHT? "JOHN SMITH, JR.",25,148
Here's the rule: you must put quotation marks around any INPUT 
string that contains a comma.
                                                    LINE INPUT
                                         If you say ___ 
10 LINE INPUT "PLEASE TYPE YOUR NAME...";N$
the computer will say:
PLEASE TYPE YOUR NAME...
Then the computer will wait for you to type your name. You do not 
have to put quotation marks around your name, even if your name 
contains a comma. LINE INPUT means: the entire line that the 
person inputs will become the string, even if the line contains a 
comma.
                                         Notice that the LINE 
INPUT statement does not make the computer automatically print a 
question mark. And notice that the variable must be a string 
(such as N$), not a number.

                                                      INPUT$
                                         This program reveals 
private information about MARY:
10 PRINT "MARY SECRETLY WISHES TO KISS A COW"
                                         Here's how to protect 
that program, so only people who know the ``secret password'' can 
run it. . . . 
                                         First, invent a secret 
password. Let's make it be ``TUNA''.
                                         Here's the program:
5 INPUT "WHAT'S THE SECRET PASSWORD";P$
10 IF P$="TUNA" THEN PRINT "MARY SECRETLY WISHES TO KISS A C
OW" ELSE PRINT "YOU ARE AN UNAUTHORIZED USER"
Line 5 asks the person to type the secret password. Whatever the 
person types is called P$. If the person types TUNA, line 10 
makes the computer say:
MARY SECRETLY WISHES TO KISS A COW
But if the person does not type TUNA, the computer says ``YOU ARE 
AN UNAUTHORIZED USER'' and refuses to reveal Mary's secret 
desire.
                                         This program's better:
5 PRINT "PLEASE TYPE THE SECRET PASSWORD"
6 P$=INPUT$(4)
10 IF P$="TUNA" THEN PRINT "MARY SECRETLY WISHES TO KISS A C
OW" ELSE PRINT "YOU ARE AN UNAUTHORIZED USER"
Line 5 makes the computer say:
PLEASE TYPE THE SECRET PASSWORD
Line 6 waits for the person to input 4 characters. The characters 
that the person inputs will become P$. For example, suppose the 
person types T, then U, then N, then A; then P$ will become TUNA 
and the computer will reveal Mary's secret.
                                         While the person inputs 
the 4 characters, they won't appear on the screen; they'll be 
invisible. That's to prevent other people in the room from 
peeking at the screen and noticing the password.
                                         After typing the 4 
characters, the person does not have to press the ENTER key. As 
soon as the person types the 4th character, the computer makes P$ 
be the 4 characters that the person typed.
  Broken computer This devilish program makes your computer 
pretend to be broken, so that whenever you press the W key your 
screen shows an F instead:
10 CLS
20 A$=INPUT$(1)
30 IF A$="W" THEN PRINT "F"; ELSE PRINT A$;
40 GO TO 20
  Line 10 clears the screen (makes the screen go blank), so that 
your friends don't see the program. Line 20 waits for you to type 
1 character. Line 30 says: if the character you typed was W, 
print an F on the screen instead; otherwise, print the character 
you typed. Line 40 makes the routine repeat, forever. For 
example, if you try to type ``THE WEATHER IS WONDERFUL'', you'll 
see this on the screen instead:
THE FEATHER IS FONDERFUL
  For an even wilder time, tell the computer to change each ``E'' 
to ``OOGA'', by changing line 30 to this:
30 IF A$="E" THEN PRINT "OOGA"; ELSE PRINT A$;
Then if you try to type ``WE ARE HERE'', you'll see this on the 
screen instead:
WOOGA AROOGA HOOGAROOGA
  Abridged literature This program gives you a choice of 
literature:
10 PRINT "WELCOME TO THE WORLD'S GREAT LITERATURE, ABRIDGED"
20 PRINT "WHICH KIND OF LITERATURE WOULD YOU LIKE?"
30 PRINT "N: NOVEL"
40 PRINT "P: POEM"
50 PRINT "PLEASE PRESS N OR P"
60 A$=INPUT$(1)
70 IF A$="N" THEN GO TO 100
80 IF A$="P" THEN GO TO 200
90 GO TO 50
100 PRINT "HE: I LOVE YOU"
110 PRINT "SHE: I'M PREGNANT"
120 PRINT "HE: LET'S GET MARRIED"
130 PRINT "SHE: LET'S GET DIVORCED"
140 PRINT "HE: LET'S GET BACK TOGETHER"
150 PRINT "SHE: TOO BAD YOU DIED IN THE WAR, BUT I'LL NEVER 
FORGET YOU!"
160 END
200 PRINT "NOSES"
210 PRINT "BLOWSES"
  Lines 10-50 make the computer print:
WELCOME TO THE WORLD'S GREAT LITERATURE, ABRIDGED
WHICH KIND OF LITERATURE WOULD YOU LIKE?
N: NOVEL
P: POEM
PLEASE PRESS N OR P
  Line 60 makes the computer wait for you to press a key. You do 
not have to press the ENTER key afterwards.
  If you press the N key, line 70 sends the computer to line 100, 
which prints an abridged novel. If you press the P key instead, 
line 80 sends the computer to line 200, which prints an abridged 
poem.
  If you press neither N nor P, the computer arrives at line 90, 
which sends the computer back to line 50, which reminds you to 
press N or P.

        JOYSTICK VERSUS MOUSE
                                         Instead of using the 
keyboard, you can input by using a joystick or mouse.

                                                     Joystick
                                         A joystick is a stick 
that sticks up from a box. You can wiggle the stick in all four 
directions (left, right, forward, and back) and diagonally.
                                         In line 100 of your 
program, if you want the computer to look at the joystick, say:
100 X=STICK(0): Y=STICK(1)
That line makes X become a number that indicates how far the 
joystick is being pulled to the right, and Y become a number that 
indicates how far the joystick is being pushed forward. To make 
the computer print X and Y on your screen, say:
110 PRINT X,Y
                                         To make the computer 
look at the joystick again and again, repeatedly, create a loop, 
by adding this line:
120 GO TO 100
Then as you wiggle the joystick, you can watch the numbers on the 
screen change.
                                         Besides printing the 
numbers X and Y on the screen, you can use the numbers X and Y in 
graphics statements (such as PLOT, LINE, and CIRCLE), so that the 
joystick controls the location of graphics shapes on the screen. 
You can also use the X and Y numbers in the SOUND statement, so 
that the joystick controls the pitch of musical sounds: moving 
the joystick will change the pitch.

                                                       Mouse
                                         A mouse is a small box 
about the size of a pack of cigarettes. You can slide the mouse 
across your desk in all four directions (left, right, forward, 
and back) and diagonally.
                                         Some versions of BASIC 
let your program contain commands to handle a mouse. Those 
commands are called mouse commands.
                                         (GWBASIC and QBASIC do 
not let programs contain mouse commands. If you're using GWBASIC 
or QBASIC, skip ahead to the next page.)
                                         If your computer's BASIC 
understands mouse commands, and you want the computer to look at 
the mouse in line 100 of your program, say this:
100 M=MOUSE(0): X=MOUSE(1): Y=MOUSE(2)
In that line, the ``M=MOUSE(0)'' makes the computer look at the 
mouse. The rest of the line makes X become a number that 
indicates how far the mouse was moved to the right, and Y become 
a number that indicates how far the mouse was moved forward. To 
make the computer print X and Y on your screen, say:
110 PRINT X,Y
                                         To make the computer 
look at the mouse again and again repeatedly, create a loop by 
adding this line:
120 GO TO 100
Then as you move the mouse across your desk, you can watch the 
numbers on the screen change.

          SWAP
  Modern computers understand the word SWAP:
10 A=4: B=9
20 SWAP A,B
30 PRINT A;B
  Line 10 says A is 4 and B is 9. Line 20 swaps A with B, so that 
A becomes 9, and B becomes 4. Line 30 prints:
 9  4
  If your computer is old-fashioned and doesn't understand the 
word SWAP, replace line 20 by this:
20 S=A: A=B: B=S
  That example swapped numbers. You can also swap strings:
10 A$="HORSE": B$="CART"
20 SWAP A$,B$
30 PRINT A$;" ";B$
Line 10 says A$ is ``HORSE'' and B$ is ``CART''. Line 20 swaps A$ 
with B$, so that A$ becomes ``CART'', and B$ becomes ``HORSE''. 
Line 30 puts the CART before the HORSE:
CART HORSE
If your computer doesn't understand SWAP, replace line 20 by 
this:
20 S$=A$: A$=B$: B$=S$
Don't forget the dollar signs!
                                               Shuffling
                             Here are some cards:
Queen of Hearts
Jack of Diamonds
Ace of Spades
Joker
King of Clubs
                             Let's shuffle them, to put them into 
a random order.
                             To begin, put the list of cards into 
a DATA statement:
10 DATA QUEEN OF HEARTS,JACK OF DIAMONDS,ACE OF SPADES,JOKER,KING 
OF CLUBS
                             We have 5 cards:
20 N=5
                             Let the Queen of Hearts be called 
X$(1), the Jack of Diamonds be called X$(2), the Ace of Spades be 
called X$(3), the Joker be called X$(4),and the King of Clubs be 
called X$(5):
30 DIM X$(N)
40 FOR I = 1 TO N: READ X$(I): NEXT
                             Shuffle the cards, by using the 
following strategy. . . . 
                             Swap the card N with a random card 
before it (or with itself); then swap card N-1 with a random card 
before it (or with itself); then swap card N-2 with a random card 
before it (or with itself); etc. Keep doing that, until you 
finally reach card 2, which you swap with a random card before it 
(or with itself). Here's the code:
50 RANDOMIZE
60 FOR I = N TO 2 STEP -1: SWAP X$(I),X$(RND(I)): NEXT
If your computer doesn't understand SWAP, replace ``SWAP 
X$(I),X$(RND(I))'' by this:
R=RND(I): S$=X$(I): X$(I)=X$(R): X$(R)=S$
If your computer doesn't understand the word RANDOMIZE, or 
doesn't understand that RND(I) is a random number from 1 to I, 
you must make further changes.
                             Finally, print the shuffled deck:
70 FOR I = 1 TO N: PRINT X$(I): NEXT
                             The computer will print something 
like this:
KING OF CLUBS
JOKER
JACK OF DIAMONDS
QUEEN OF HEARTS
ACE OF SPADES
                             To shuffle a larger deck, change 
just lines 10 and 20.
                     Sorting
  Putting words in alphabetical order ___ or putting numbers in 
numerical order ___ is called sorting.
  Short Three-Line Sort Here are a dozen names: Sue, Ann, Joe, 
Alice, Ted, Jill, Fred, Al, Sam, Pat, Sally, Moe. Let's make the 
computer alphabetize them (sort them).
  To begin, put the list of names into a DATA statement:
10 DATA SUE,ANN,JOE,ALICE,TED,JILL,FRED,AL,SAM,PAT,SALLY,MOE
  We have 12 names:
20 N=12
  Let Sue be called X$(1), Ann be called X$(2), Joe be called 
X$(3), etc. Here's how:
30 DIM X$(N)
40 FOR I = 1 TO N: READ X$(I): NEXT
  Alphabetize the names, by using the following strategy. . . . 
  Compare the first name against the second; if they're not in 
alphabetical order, swap them. Compare the second name against 
the third; if they're not in alphabetical order, swap them. 
Compare the third name against the fourth; if they're not in 
alphabetical order, swap them. Continue that process, until you 
finally compare the last two names. But each time you swap, you 
must start the whole process over again, to make sure the 
preceding names are still in alphabetical order. Here's the code:
50 FOR I = 1 TO N-1
60     IF X$(I)>X$(I+1) THEN SWAP X$(I),X$(I+1): GO TO 50
70 NEXT
  Finally, print the alphabetized list:
80 FOR I = 1 TO N: PRINT X$(I): NEXT
The computer will print:
AL
ALICE
ANN
FRED
JILL
JOE
MOE
PAT
SALLY
SAM
SUE
TED
  In that program, the sorting occurs in lines 50-70. Those three 
short lines are called the Short Three-Line Sort.
  Those three lines form a loop. The part of the loop that the 
computer encounters the most often is the phrase ``IF 
X$(I)>X$(I+1)''. In fact, if you tell the computer to alphabetize 
a list of names that's long (several hundred names), the computer 
spends the majority of its time repeatedly handling ``IF 
X$(I)>X$(I+1)''.
  How long will the computer take to handle a long list of names? 
The length of time depends mainly on how often the computer 
encounters the phrase ``IF X$(I)>X$(I+1)''.
  If the list contains N names, the number of times that the 
computer encounters the phrase ``IF X$(I)>X$(I+1)'' is 
approximately N3/8. Here are some examples:
N (number of names)N3/8 (approximate number of encounters)
    10                      125
    12                      216
    20                    1,000
    40                    8,000
   100                  125,000
 1,000              125,000,000
10,000          125,000,000,000
  For example, the chart says that a list of 12 names requires 
approximately 216 encounters.
                                                     The 216 is 
just an approximation: the exact number of encounters depends on 
which list of names you're trying to alphabetize. If the list is 
nearly in alphabetical order already, the number of encounters 
will be less than 216; if the list is in reverse alphabetical 
order, the number of encounters will be more than 216; but if the 
list is typical (not yet in any particular order), the number of 
encounters will be about 216. For the list that we tried (Sue, 
Ann, Joe, Alice, Ted, Jill, Fred, Al, Sam, Pat, Sally, Moe), the 
exact number of encounters happens to be 189, which is close to 
216.
  How long will your computer take to finish sorting? The length 
of time depends on which computer you have, how many names are in 
the list, and how long each name is. A typical microcomputer 
(handling a list of typical names) requires .01 seconds per 
encounter. Multiplying the number of encounters by .01 seconds, 
you get:
Number of namesEncounters (N3/8)               Time                     
    10                    125            1.25 secs
    12                    216            2.16 secs
    20                  1,000           10    secs
    40                  8,000           80    secs =  1.3 minutes
   100                125,000        1,250    secs = 20.8 minutes
 1,000            125,000,000    1,250,000    secs = 14.4 days
10,000        125,000,000,0001,250,000,000    secs = 39.6 years
  Moral: never let a 70-year-old programmer alphabetize a list of 
10,000 names by using the Short Three-Line Sort ___ because when 
the computer finishes running the program (39.6 years later), the 
programmer will probably be dead!
  Fancy Three-Line Sort In the Short Three-Line Sort, the end of 
line 60 says ``GO TO 50''. For an interesting experiment, replace 
the ``GO TO 50'' by ``IF I>1 THEN I=I-1: GO TO 60'', so that line 
60 looks like this:
60     IF X$(I)>X$(I+1) THEN SWAP X$(I),X$(I+1): IF I>1 THEN 
I=I-1: GO TO 60
  Even though that new, fancy version of line 60 is longer to 
type than the original, the computer handles it more quickly, 
because it tells the computer to GO TO line 60 instead of forcing 
the computer to go all the way back to line 50. The fancy version 
is called the Fancy Three-Line Sort.
  If you feed the computer the Fancy Three-Line Sort (instead of 
the Short Three-Line Sort), the computer encounters the ``IF 
X$(I)>X$(I+1)'' less often: just N2/2 times (instead of N3/8).
Number of namesEncounters (N2/2)         Time                
    10                50           .50 secs
    12                72           .72 secs
    20               200          2    secs
    40               800          8    secs
   100             5,000         50    secs
 1,000           500,000      5,000    secs = 1.4 hours
10,000        50,000,000    500,000    secs = 5.8 days
  Now you can hire the 70-year old programmer: to alphabetize 
10,000 names, he'll need just 5.8 days instead of 39.6 years. By 
changing just the end of line 60, we saved almost 40 years of 
computer time ___ and the programmer's job!
  Super-Fancy Three-Line Sort To reduce the time even further, 
use the Super-Fancy Three-Line Sort instead, which is:
50 FOR I = 1 TO N-1
60     FOR J = I TO 1 STEP -1: IF X$(J)>X$(J+1) THEN SWAP 
X$(J),X$(J+1): NEXT
70 NEXT I
  When typing the Super-Fancy Three-Line Sort, make sure you type 
line 60 correctly: you must put the IF on the same line as the 
NEXT. In line 70, make sure you put the ``I'' after NEXT; 
otherwise, the computer might think you mean NEXT J.
  For the Super-Fancy Three-Line Sort, the number of times the 
computer encounters the phrase ``IF X$(J)>X$(J+1)'' is just N2/4:
Number of namesEncounters (N2/4)         Time                
    10                25           .25 secs
    12                36           .36 secs
    20               100          1    secs
    40               400          4    secs
   100             2,500         25    secs
 1,000           250,000      2,500    secs = 41.7 minutes
10,000        25,000,000    250,000    secs =  2.9 days
  Six-Line Sort The Six-Line Sort reduces the time even further.
  To construct the Six-Line Sort, begin with the Super-Fancy 
Three-Line Sort, but change each +1 to +D, and change each -1 to 
-D, so that you get:
50 FOR I = 1 TO N-D
60     FOR J = I TO 1 STEP -D: IF X$(J)>X$(J+D) THEN SWAP 
X$(J),X$(J+D): NEXT
70 NEXT I

                                                     D begins by 
being N ___ 
42 D=N
but then decreases, so that it becomes a fifth of its original 
value:
44 D=INT(D/5)+1
After performing lines 50-70 for that D, check whether D is down 
to 1 yet; if it isn't, repeat the process:
75 IF D>1 THEN GO TO 44

  So altogether, the complete Six-Line Sort looks like this:
42 D=N
44 D=INT(D/5)+1
50 FOR I = 1 TO N-D
60     FOR J = I TO 1 STEP -D: IF X$(J)>X$(J+D) THEN SWAP 
X$(J),X$(J+D): NEXT
70 NEXT I
75 IF D>1 THEN GO TO 44
  For the Six-Line Sort, the number of times the computer 
encounters the phrase ``IF X$(J)>X$(J+D)'' is just 
1.5*(N-1)^(4/3):
Number of namesEncounters      Time                    
    10             28        .28 secs
    12             37        .37 secs
    20             76        .76 secs
    40            198       1.98 secs
   100            687       6.87 secs
 1,000         14,980     149.80 secs =  2.5 minutes
10,000        323,122   3,231.22 secs = 53.9 minutes
  Notice that the Six-Line Sort handles 10,000 names in 53.9 
minutes. That's much faster than the Super-Fancy Three-Line Sort, 
which takes 2.9 days. But to handle just 10 names, the Six-Line 
Sort does not run faster than the Super-Fancy Three-Line Sort. So 
use the Six-Line Sort just for handling long lists of names.
  To make the Six-Line Sort even faster, add this line:
1 DEFINT A-Z
That tells the computer that none of the variables stands for a 
decimal. By saying DEFINT A-Z, you enable the computer to run the 
program 20% faster, so that the timing looks like this:
Number of names      Time                
    10             .2 secs
    12             .3 secs
    20             .6 secs
    40            1.6 secs
   100            5.5 secs
 1,000          120   secs =  2 minutes
10,000        2,580   secs = 43 minutes
  We've sure come a long way! Our first attempt (the Short 
Three-Line Sort) took 39.6 years to alphabetize 10,000 names; our 
newest attempt (the Six-Line Sort with DEFINT) takes just 43 
minutes.
  If you try running those sorting methods on your computer, 
you'll find the timings are slightly different, since the exact 
timings depend on which computer you have, the length of each 
name, and how badly the names are out of order.
  Famous sorts Although I ``invented'' all those sorting methods, 
most of them are just slight improvements on methods that were 
developed by others. For example, the Super-Fancy Three-Line Sort 
is a slight improvement on the Shuttle Sort, which was invented 
by Shaw & Trimble in 1983. The Six-Line Sort is a slight 
improvement on the Shell Sort, which was invented by Donald Shell 
in 1959 and further developed by Hibbard & Boothroyd in 1963, 
Peterson & Russell in 1971, and Knuth in 1973.
  Phone directory Suppose you want to alphabetize this phone 
directory:
Name    Phone number
Mary Smith277-8139
John Doe513-9134
Russ Walter666-2666
Information555-1212
  Just use one of the alphabetizing programs I showed you! Type 
the DATA like this:
10 DATA SMITH MARY 277-8139,DOE JOHN 513-9134
20 DATA WALTER RUSS 666-2666,INFORMATION 555-1212
The computer will print:
DOE JOHN 513-9134
INFORMATION 555-1212
SMITH MARY 277-8139
WALTER RUSS 666-2666

                                                     Sorting 
numbers Suppose you want to put a list of numbers into increasing 
order. For example, if the numbers are 51, 4.257, -814, 62, and 
.2, let's make the computer print:
-814
  .2
 4.257
 51
 62
                                                     To do that, 
just use one of the alphabetizing programs I showed you ___ but 
in the DATA statement, put the numbers instead of strings; and 
remove the dollar signs (say X instead of X$).
                                                     To put a 
list of numbers into decreasing order, begin by writing a program 
that puts them into increasing order, and then change line 60 
from ``>X'' to ``<X''.

           ON
  The computer understands the word ``ON''.

     ON . . . GO TO
  In your program, you can say:
50 ON N GO TO 80,100,20,350
That means: go to either 80, 100, 20, or 350; the decision 
depends on what N is. In other words:
If N is 1, go to 80.
If N is 2, go to 100.
If N is 3, go to 20.
If N is 4, go to 350.
  In that example, if N is not 1, 2, 3, or 4, the computer will 
not go to line 80 or 100 or 20 or 350; instead, the computer will 
proceed to the line underneath line 50 (which is probably line 
60).
  Exception: if N is greater than 255 or a negative number (such 
as -1), the computer thinks you're crazy, and so the computer 
gripes at you instead of proceeding to line 60.
  Another exception: if N is a decimal (such as 3.1), the 
computer treats N as if it were a whole number (3); so in that 
example, if N is 3.1, the computer will go to line 20.
                             Christmas Remember the Christmas 
carol called ``The Twelve Days of Christmas''? The first three 
verses go like this:
ON THE FIRST DAY OF CHRISTMAS, MY TRUE LOVE SENT TO ME
A PARTRIDGE IN A PEAR TREE.

ON THE SECOND DAY OF CHRISTMAS, MY TRUE LOVE SENT TO ME
TWO TURTLE DOVES...AND
A PARTRIDGE IN A PEAR TREE.

ON THE THIRD DAY OF CHRISTMAS, MY TRUE LOVE SENT TO ME
THREE FRENCH HENS,
TWO TURTLE DOVES...AND
A PARTRIDGE IN A PEAR TREE.
                             This program prints the final verse:
10 PRINT "ON THE TWELFTH DAY OF CHRISTMAS, MY TRUE LOVE SENT TO 
ME"
20 PRINT "TWELVE DRUMMERS DRUMMING,"
30 PRINT "ELEVEN PIPERS PIPING,"
40 PRINT "TEN LORDS A-LEAPING,"
50 PRINT "NINE LADIES DANCING,"
60 PRINT "EIGHT MAIDS A-MILKING,"
70 PRINT "SEVEN SWANS A-SWIMMING,"
80 PRINT "SIX GEESE A-LAYING,"
90 PRINT "FIVE GO---OLD RINGS,"
100 PRINT "FOUR CALLING BIRDS,"
110 PRINT "THREE FRENCH HENS,"
120 PRINT "TWO TURTLE DOVES...AND"
130 PRINT "A PARTRIDGE IN A PEAR TREE."
                             This program prints all twelve 
verses:
1 DATA FIRST,SECOND,THIRD,FOURTH,FIFTH,SIXTH,SEVENTH,EIGHTH,NINTH
2 DATA TENTH,ELEVENTH,TWELFTH                                    
3 FOR V = 1 TO 12                                                
4      READ W$                                                   
10     PRINT "ON THE ";W$;" DAY OF CHRISTMAS, MY TRUE LOVE SENT 
TO ME"
11     ON V GO TO 130,120,110,100,90,80,70,60,50,40,30,20
20     PRINT "TWELVE DRUMMERS DRUMMING,"
30     PRINT "ELEVEN PIPERS PIPING,"
40     PRINT "TEN LORDS A-LEAPING,"
50     PRINT "NINE LADIES DANCING,"
60     PRINT "EIGHT MAIDS A-MILKING,"
70     PRINT "SEVEN SWANS A-SWIMMING,"
80     PRINT "SIX GEESE A-LAYING,"
90     PRINT "FIVE GO---OLD RINGS,"
100    PRINT "FOUR CALLING BIRDS,"
110    PRINT "THREE FRENCH HENS,"
120    PRINT "TWO TURTLE DOVES...AND"
130    PRINT "A PARTRIDGE IN A PEAR TREE."
140    PRINT
150 NEXT    
                             Lines 1 and 2 teach the computer how 
to spell the words ``FIRST'', ``SECOND'', ``THIRD'', etc. Line 3 
makes the computer do lines 4 through 140, twelve times (once for 
each verse). Lines 4 and 10 look at the data and print the top 
line of the verse. Line 11 says:
If V is 1, go to line 130 (so the computer prints A PARTRIDGE IN 
A PEAR TREE).

If V is 2, go to line 120 (so the computer prints TWO TURTLE 
DOVES...AND A PARTRIDGE IN A PEAR TREE).

If V is 3, go to line 110 (so the computer prints THREE FRENCH 
HENS, TWO TURTLE DOVES...AND A PARTRIDGE IN A PEAR TREE).

And so on, for each verse.

                                            ON . . . GOSUB
                             You can say:
50 ON N GOSUB 80,100,20,350
                             That means:
If N is 1, GOSUB 80.
If N is 2, GOSUB 100.
If N is 3, GOSUB 20.
If N is 4, GOSUB 350.

     ON ERROR GO TO
  If the computer finds an error while running your program, the 
computer wants to gripe. But instead of letting the computer 
gripe, you can force the computer to do something different.
  For example, you can tell the computer, ``If you find an error 
in lines 50-70, don't gripe; instead of griping, do the special 
routine that begins at line 1000.'' To tell the computer that, 
insert these lines:
49 ON ERROR GO TO 1000
71 ON ERROR GO TO 0
Lines 49 and 71 tell the computer, ``If you find an error between 
lines 49 and 71, go to the special routine that begins at line 
1000.''
  Invent your own special routine, so that it begins at line 1000 
and continues onto lines 1010, 1020, etc.
  The bottom line of your special routine should tell the 
computer where to go afterwards.
  For example, suppose that after the routine is done, you want 
the computer to go back to line 30 (to try again). Just put this 
line at the bottom of the routine:
1090 RESUME 30
That way, if an error occurs between lines 49 and 71, the 
computer will do the routine in lines 1000-1080, then come to 
line 1090, which sends the computer back to line 30.
  The special routine (in lines 1000-1090) is called an 
error-handling routine or an error trap. Its bottom line says 
RESUME. (By contrast, the bottom line of an ordinary subroutine 
says RETURN instead.)
  To separate the main routine (lines 10-999) from the 
error-handing routine (lines 1000-1090), the bottom line of the 
main routine should say END, like this:
999 END
  Instead of saying RESUME 30, which sends the computer back to 
line 30, you can send the computer back to any other line you 
wish. For example, you can say RESUME 80.
  If you don't put any number after RESUME, the computer will go 
back to the line that contained the error.
  If you say RESUME NEXT, the computer will go to the line 
underneath the line that contained the error. To make RESUME NEXT 
work properly, the line that contained the error should consists 
of just one statement (instead of statements separated by 
colons).

                  MEMORY CELLS
                             The computer's main memory consists 
of many memory cells. Each cell holds an integer from 0 to 255. 
For example, cell #7512 might hold the integer 17.

                                                 PEEK
                             To find out what number's in cell 
#7512, say:
PRINT PEEK(7512)
That makes the computer peek at cell #7512, find the number in 
that cell, and print that number on your screen. The number it 
prints will be an integer from 0 to 255. For example, it might be 
17.

                                                 POKE
                             The memory contains two kinds of 
cells. One kind, called ROM, contains information permanently. 
The other kind, called RAM, contains information temporarily, and 
you can change that information. When you turn the computer on, 
each RAM cell contains a 0, but you can change the zeros to other 
numbers.
                             If you say ___ 
POKE 7512,14
the computer will try to put the number 14 into cell #7512. If 
cell #7512 is in the RAM, the computer will succeed. If cell 
#7512 is in the ROM, the computer will give up, since the 
information in ROM cells is permanent and can't be changed.
                             To find out whether the computer 
successfully put the number 14 into cell #7512, say:
PRINT PEEK(7512)
If the computer prints 14, the computer successfully poked. If 
the computer prints a different number instead, the computer's 
POKE was unsuccessful, which means cell #7512 is in the ROM and 
therefore can't be changed.
                             When you turn the computer on, the 
ROM cells contain their permanent information, but the RAM cells 
are ``blank''; each RAM cell contains 0. To change the numbers in 
the RAM cells, say POKE.

                                            How RAM is used
                             Whenever you type a new program or 
command or data, the computer temporarily stores what you typed 
in the RAM.
                             For example, if you type the word 
CAB (because you're writing a program about taxicabs), the 
computer temporarily puts the ASCII code numbers for C, A, and B 
into RAM cells. Since C's ASCII code number is 67, A's is 65, and 
B's is 66, the computer puts the numbers 67, 65, and 66 into 
three RAM cells.
                             As you type more programs, commands, 
and data, the computer puts their ASCII code numbers into RAM 
cells. Into other RAM cells, the computer puts notes about what 
you and the computer are doing.
                             If you say to POKE a number into a 
RAM cell, beware: the computer might already be using that cell 
to hold an important note. The number you POKE into the cell will 
replace the computer's note. The computer will forget the note, 
get confused, and go crazy. If the RAM cell contained a note 
about your program, the computer might wreck your program; if the 
RAM cell contained a note about the disk drive, the computer 
might go so crazy that it will turn the drive on and wreck all 
the information on the disk!
                             So before you say POKE, find out 
which RAM cells the computer uses for which purposes ___ and as 
an extra precaution, remove your disk from the drive. Don't 
reinsert the disk until you've turned off the computer and 
started fresh again.

        SEQUENTIAL DATA FILES
  Here's a simple program:
10 PRINT "EAT"
20 PRINT 2+2
30 PRINT "EGGS"
  It makes the computer print this message onto your screen:
EAT
 4
EGGS
  Instead of printing that message onto your screen, let's make 
the computer print the message onto your disk. Here's how. . . . 

           OPEN FOR OUTPUT
  This program prints the message onto your disk, instead of onto 
your screen:
5 OPEN "SUE" FOR OUTPUT AS 1
10 PRINT#1, "EAT"
20 PRINT#1, 2+2
30 PRINT#1, "EGGS"
40 CLOSE
  Lines 10-30 make the computer print the message onto your disk, 
instead of onto your screen. Each line says PRINT#1, which means: 
print onto the disk.
  Line 5 is an introductory line that tells the computer where on 
the disk to print the message. Line 5 says: find a blank place on 
the disk, call it ``SUE'', and make ``SUE'' be file#1. So 
PRINT#1, will mean: print onto file#1, which is SUE.
  Any program that says OPEN should also say CLOSE, so line 40 
says CLOSE. The CLOSE line makes the computer put some 
``finishing touches'' on SUE, so that SUE becomes a perfect, 
finished file.
  When you RUN that program, the computer will automatically put 
onto the disk a file called ``SUE'' that contains this message:
EAT
 4
EGGS
  After running the program, if you want to see the names of all 
the files on the disk, type FILES (or DIRECTORY or CATALOG or 
whatever other word your computer uses). The computer will print 
the names of all the files ___ and one of the names it prints 
will be SUE.
                                                  OPEN FOR INPUT
                                         To see the message 
that's in SUE, run this program, which inputs from SUE and prints 
onto your screen:
5 OPEN "SUE" FOR INPUT AS 1

10 INPUT#1, A$
11 PRINT A$

20 INPUT#1, B
21 PRINT B

30 INPUT#1, C$
31 PRINT C$

40 CLOSE
                                         Line 5 prepares the 
computer to input from SUE.
                                         Line 10 inputs A$ from 
SUE, so A$ is EAT. Line 11 prints EAT onto your screen.
                                         Line 20 inputs B from 
SUE, so B is 4. Line 21 prints 4 onto your screen.
                                         Line 30 inputs C$ from 
SUE, so C$ is EGGS. Line 31 prints EGGS onto your screen. So 
altogether, on your screen you'll see:
EAT
 4
EGGS
                                         Line 40 tells the 
computer that you're done using SUE for a while (until you say 
OPEN again).

                                                  OPEN FOR APPEND
                                         After you've put SUE 
onto the disk, so that SUE consists of EAT and 4 and EGGS, try 
running this program:
10 OPEN "SUE" FOR APPEND AS 1
20 PRINT#1, "GOOD MORNING!"
30 CLOSE
                                         In line 10, the word 
APPEND tells the computer to keep adding onto SUE. So when the 
computer comes to line 20, it adds ``GOOD MORNING'' onto SUE, and 
SUE becomes this:
EAT
 4
EGGS
GOOD MORNING!

                                                      Erasing
                                         For your next 
experiment, try running this program:
10 OPEN "SUE" FOR OUTPUT AS 1
20 PRINT#1, "PICKLES ARE PLEASANT"
30 CLOSE
                                         Since line 10 does not 
say APPEND, the computer will not keep adding onto SUE. Instead, 
the computer erases everything that's been in SUE. So when the 
computer finishes processing line 10, SUE's become blank.
                                         Line 20 puts ``PICKLES 
ARE PLEASANT'' into SUE. So at the end of the program, SUE 
includes ``PICKLES ARE PLEASANT''; but SUE does not include EAT 
and 4 and EGGS and ``GOOD MORNING'', which have all been erased.
                      Loops
  This program lets you put the names of all your friends onto 
the disk:
10 OPEN "FRIENDS" FOR OUTPUT AS 1
20 PRINT "PLEASE TYPE A FRIEND'S NAME (OR THE WORD 'END')"
30 INPUT F$: IF F$="END" THEN CLOSE: END
40 PRINT#1, F$
50 GO TO 20
  Line 10 makes the computer find a blank space on the disk and 
call it FRIENDS. Line 20 makes the computer print:
PLEASE TYPE A FRIEND'S NAME (OR THE WORD 'END')
  Line 30 prints a question mark and waits for you to type 
something; whatever you type will be called F$. For example, if 
you type JOAN WILLIAMS, then F$ will be JOAN WILLIAMS, and line 
40 prints the name JOAN WILLIAMS onto the disk.
  Line 50 creates a loop, so that you can type as many names as 
you wish. (Remember to press the ENTER key after each name.)
  When you've finished typing the names of all your friends, type 
the word END. Then the last part of line 30 will make the 
computer CLOSE the file and END the program.
  This program makes the computer look at the FRIENDS file and 
copy all its names to your screen:
10 OPEN "FRIENDS" FOR INPUT AS 1
20 IF EOF(1) THEN PRINT "THOSE ARE ALL THE FRIENDS": CLOSE: END
30 INPUT#1, F$
40 PRINT F$
50 GO TO 20
  Line 10 prepares the computer to input from the FRIENDS file. 
Line 20 is special; I'll explain it later. Line 30 makes the 
computer input a string from the file and call the string F$; so 
F$ becomes the name of one of your friends. Line 40 prints that 
friend's name onto your screen. Line 50 creates a loop, so that 
the names of all your friends are printed on the screen.
  Eventually, the computer will reach the end of the file, and 
there won't be any more names to input from the file. Line 20 
says: if the computer reaches the End Of the File and can't input 
any more names from it, the computer should print on your screen 
``THOSE ARE ALL THE FRIENDS'', then CLOSE the file and END the 
program.

                       LOF
  In the middle of your program, if you say PRINT LOF(1), the 
computer will tell you the Length Of the File: it will tell you 
how many bytes are in the file.

                 Multiple files
  If you want the computer to handle two files simultaneously, 
use two OPEN statements. At the end of the first OPEN statement, 
say ``AS 1''; at the end of the second OPEN statement, say ``AS 
2''.
  For the second file, say PRINT#2 instead of PRINT#1, say 
INPUT#2 instead of INPUT#1, say EOF(2) instead of EOF(1), and say 
LOF(2) instead of LOF(1).

                  How to CLOSE
  The CLOSE statement closes all files. To be more specific, you 
can say CLOSE 1 (which closes just the first file) or CLOSE 2 
(which closes just the second).
  Whenever you're done using a file, CLOSE it immediately. When 
you say CLOSE, the computer puts finishing touches on the file 
that protect the file against damage.
  Suppose that halfway through your program, you finish using 
file 2 but want to continue using file 1. Say CLOSE 2 there, and 
delay saying CLOSE 1 until later.


            RANDOM ACCESS
  On a disk, you can store two kinds of data files. The simple 
kind is called a sequential-access data file; the complicated 
kind is called a random-access (or relative-access or 
direct-access) data file. You've already learned how to create 
and retrieve a sequential-access file. Now let's look at 
random-access.
  Though more complicated than sequential-access data files, 
random-access data files have an advantage: they let you skip 
around. In a sequential-access data file, you must look at the 
first item of data, then the second, then the third, etc. In a 
random-access data file, you can look at the seventh item of 
data, then skip directly to the tenth, then hop back to the 
third, then skip directly to the sixth, etc.
  Each item is called a record. The number of characters (bytes) 
in the record is called the record's length. For example, if a 
record contains 30 characters, the record's length is 30. In a 
random-access file, all the records must have the same length as 
each other.

                 PUT
  Let's create a random-access file called JIM. Let's make JIM's 
record length be 20, so that each record will contain 20 
characters. Here's how:
5 OPEN "JIM" AS 1 LEN=20: FIELD 1, 20 AS X$
  Let's make JIM's 7th record be ``LOVE MAKES ME GIGGLE'' (which 
contains 20 characters):
10 LSET X$="LOVE MAKES ME GIGGLE": PUT 1,7
  Let's make JIM's 9th record be ``PLEASE HOLD MY HAND'':
20 LSET X$="PLEASE HOLD MY HAND": PUT 1,9
Since JIM's record length is supposed to be 20 characters but 
``PLEASE HOLD MY HAND'' contains just 19 characters, the computer 
will automatically add a blank to the end of ``PLEASE HOLD MY 
HAND''.
  Let's make JIM's 4th record be ``I LOVE LUCY'':
30 LSET X$="I LOVE LUCY": PUT 1,4
The computer will automatically add blanks to the end of ``I LOVE 
LUCY''.
  To finish the program, say:
40 CLOSE

                 GET
  This program makes the computer tell you JIM's 7th item:
5 OPEN "JIM" AS 1 LEN=20: FIELD 1, 20 AS X$
10 GET 1,7: PRINT X$
20 CLOSE

         Multi-field records
  If you want each record to be a pair of strings, begin like 
this:
5 OPEN "JIM" AS 1 LEN=34: FIELD 1, 30 AS X$, 4 AS Y$
10 LSET X$="LOVE MAKES ME GIGGLE": LSET Y$="WOW": PUT 1,7
etc.

                                         Line 5 makes each record 
consist of two fields. The first field is a 30-character string 
called X$; the second field is a 4-character string called Y$.
                                         Line 10 says to PUT into 
the 7th record this pair of strings: ``LOVE MAKES ME GIGGLE'' and 
``WOW''.

                                                        LOC
                                         While using a 
random-access file, if you say PRINT LOC(1), the computer tells 
you which record it just dealt with: it tells you the record 
LOCation. For example, if you say ``PUT 1,7'' or ``GET 1,7'' and 
then say PRINT LOC(1), the computer prints the number 7.
                                         If you say ``PUT 1'' 
instead of ``PUT 1,7'', the computer will assume you mean ``PUT 
1,LOC(1)+1''. If you say ``GET 1'', the computer will assume you 
mean ``GET 1,LOC(1)+1''.

                                                  End of the file
                                         The EOF function doesn't 
work well for random-access files. To deal with the end of the 
file, use the following trick instead.
                                         Suppose you say LEN=34, 
so that 34 bytes make a record. Since the number of bytes in the 
entire file is LOF(1), and 34 bytes make a record, the number of 
records in the file is LOF(1)/34. These lines print all the 
records:
100 FOR I = 1 TO LOF(1)/34
110     GET 1: PRINT X$;Y$
120 NEXT

                                          Restrictions on FIELD variables
                                         If you put a variable 
(such as X$) into a FIELD statement, you cannot put it into an 
ordinary ``='' statement: instead of saying X$=``LOVE MAKES ME 
GIGGLE'', you must say LSET X$=``LOVE MAKES ME GIGGLE''. You 
cannot put the variable into an INPUT statement: instead of 
saying INPUT X$, you must say INPUT A$ and then LSET X$=A$.

                                                  Numerical data
                                         On most computers, a 
random-access file must contain strings, not numbers. If you want 
to store numbers, you must turn them into strings.
                                         To turn an integer into 
a string, use the function MKI$ (MaKe from Integer). It turns the 
integer into a 2-byte string, even if the integer is long. For 
example, to turn the integer 17999 into a 2-byte string called 
X$, say FIELD 1, 2 AS X$ and say LSET X$=MKI$(17999).
                                         The function MKS$ (MaKe 
from Single-precision real) turns a real number into a 4-byte 
string. The function MKD$ (MaKe from Double-precision) turns a 
double-precision number into an 8-byte string.
                                         Suppose you turn a 
number into a string (by using MKI$, MKS$, or MKD$), and PUT the 
string into a file, and later GET the string back from the file. 
You'll want to convert the string back to a number. Use the 
function CVI (ConVert to Integer) or CVS (ConVert to 
Single-precision) or CVD (ConVert to Double-precision). For 
example, if X$ is a 2-byte string that stands for an integer, you 
can make the computer print the integer by saying PRINT CVI(X$).

                CREATE A DATABASE
  The following program creates a database, in which you can 
store information about your friends & enemies, your business & 
bills, birthdays & appointments, desires & dreads, and whatever 
else bothers you. After storing the information in the database, 
you can peek at the information, change it, expand on it, delete 
it, or do whatever else strikes your fancy.

             Chronological database
  The program consists of a main routine and 7 subroutines:
The main routine
All variables will be integers.10 DEFINT A-Z
Allow 100 topics & their data.20 DIM T$(100),D$(100)
Number of topics starts at 0.30 N=0
Ask the human for a topic.40 PRINT: PRINT "WHAT TOPIC INTERESTS 
YOU?": PRINT "(IF YOU'RE NOT SURE, TYPE A QUESTION MARK)": L
                INE INPUT T$
Do what the human wishes.50 IF T$="?" THEN GOSUB 1000 ELSE GOSUB 
2000
Go to another topic.60 GO TO 40

Subroutine 1000: tell the human what topics are in the database
If database is empty, say so.1000 IF N=0 THEN PRINT "I DON'T KNOW 
ANY TOPICS YET.": PRINT "MY MIND IS STILL BLANK.": PRINT "PLE ASE 
TEACH ME A NEW TOPIC.": RETURN
If not empty, list the topics.1010 PRINT "I KNOW ABOUT THESE 
TOPICS:": FOR I = 1 TO N: PRINT T$(I),: NEXT I: PRINT: PRINT 
"PICK 
                ONE OF THOSE TOPICS, OR TEACH ME A NEW ONE."
                1020 RETURN

Subroutine 2000: search through the database, to find the topic 
T$
Start searching.2000 FOR I = 1 TO N
If the topic is found, do 3000.2010    IF T$=T$(I) THEN GOSUB 
3000: RETURN
If not found yet, try again.2020 NEXT
If never found, do 4000.2030 GOSUB 4000
                2040 RETURN

Subroutine 3000: the topic's in the database
Tell the human about the topic.3000 PRINT "HERE'S WHAT I KNOW 
ABOUT "T$":": PRINT D$(I)
Ask whether to change the info.3010 INPUT "DO YOU WANT TO CHANGE 
THAT INFORMATION";A$
If the human says yes, do 5000.3020 IF A$="YES" OR A$="Y" THEN 
GOSUB 5000
                3030 RETURN

Subroutine 4000: the topic's not in the database
Say topic is not in database.4000 PRINT "I DON'T KNOW ANYTHING 
ABOUT "T$"."
Request info about the topic.4010 PRINT: PRINT "TELL ME ABOUT 
"T$: PRINT "(IF YOU DON'T WANT TO TELL ME, TYPE THE LETTER X)": L
                INE INPUT D$
If human wants, insert topic.4020 IF D$<>"X" THEN GOSUB 6000
                4030 RETURN

Subroutine 5000: change the info
Agree to change the info.5000 PRINT "OKAY. I'VE ERASED THAT 
INFORMATION ABOUT "T$"."
Request new info.5010 PRINT: PRINT "TYPE WHAT YOU WANT ME TO KNOW 
ABOUT "T$: PRINT "(IF YOU WANT ME TO FORGET "T$",
                 TYPE THE LETTER X)": INPUT D$
Change the info as requested.5020 IF D$="X" THEN GOSUB 7000 ELSE 
D$(I)=D$
                5030 RETURN

Subroutine 6000: insert the topic into the database
Increase the number of topics.6000 N=N+1
Append new topic & its data.6010 T$(N)=T$: D$(N)=D$
                6020 RETURN

Subroutine 7000: delete the topic from the database
Replace that topic by topic #N.7000 T$(I)=T$(N): D$(I)=D$(N)
Decrease the number of topics.7010 N=N-1
                7020 RETURN
  If your computer doesn't understand DEFINT, omit line 10. If 
your computer doesn't understand LINE INPUT, omit the word LINE 
from lines 40 and 4010.
  The program stores the topics in chronological order: if you 
begin by feeding it information about SUE and then information 
about CAROL, it will let T$(1) be SUE and let T$(2) be CAROL.

              Alphabetical database
  Instead of chronological order, you might prefer alphabetical 
order.
  For example, suppose you feed the computer information about 
SUE then CAROL then ZELDA then ALICE then JANE. Here's what the 
computer's memory would look like, in each kind of order:
Chronological orderAlphabetical order
SUE           ALICE
CAROL         CAROL
ZELDA         JANE
ALICE         SUE
JANE          ZELDA
  Which is better: chronological order or alphabetical order?
  Chronological order lets you quickly add a new name (just add 
it at the end of the list), but finding a name in the list is 
slow (since the list looks disorganized). Alphabetical order lets 
you find a name faster (since the list is alphabetized), but 
adding a new name to the alphabetized list is slow (since the 
only way to insert the new name is to make room for it by shoving 
other names out of the way).
  So which is better?
Chronological order is the simplest to program and the fastest 
for INSERTING.
Alphabetical order is the fastest for FINDING information.
  If you want to store the names in alphabetical order instead of 
chronological order, just change subroutines 2000, 6000, and 7000 
to these:
Subroutine 2000A: search through the database, to find the topic 
T$
Create L and H. 2000 L=0: H=N+1
I is the average of L and H.2010 I=INT((L+H+1)/2)
If I=H, do 4000.2020 IF I=H THEN GOSUB 4000: RETURN
If the topic is found, do 3000.2030 IF T$=T$(I) THEN GOSUB 3000: 
RETURN
Not found yet. Change H or L2040 IF T$<T$(I) THEN H=I ELSE L=I
and try again to find topic!2050 GO TO 2010

Subroutine 6000A: insert the topic into the database
Increase the number of topics.6000 N=N+1
Move other topics out of way.6010 FOR J = N TO I+1 STEP -1: 
T$(J)=T$(J-1): D$(J)=D$(
                J-1): NEXT
Insert new topic & its data.6020 T$(I)=T$: D$(I)=D$
                6030 RETURN

Subroutine 7000A: delete the topic from the database
Decrease the number of topics.7000 N=N-1
Close gap from deleted topic.7010 FOR J = 1 TO N: T$(J)=T$(J+1): 
D$(J)=D$(J+1): NEXT
                7020 RETURN
  Subroutine 2000A runs faster than chronological subroutine 
2000, because searching through an alphabetical list is faster 
than searching through a chronological list. (To search through 
the alphabetical list super-quickly, subroutine 2000A uses a 
trick called binary search.)
  Unfortunately, subroutines 6000A (which inserts) and 7000A 
(which deletes) run slower than chronological subroutines 6000 
and 7000. To get the high speed of subroutine 2000A, you must 
accept the slowness of subroutines 6000A and 7000A.
  You've seen that chronological order is fast for inserting and 
deleting but slow for searching, whereas alphabetical order is 
exactly the opposite: it's fast for searching but slow for 
inserting or deleting.

            Tree-structured database
  Instead of using chronological order or alphabetical order, 
advanced programmers use a tree. Like chronological order, a tree 
lets you insert and delete quickly. Like alphabetical order, a 
tree lets you search quickly also.
  Poets say, ``only God can make a tree.'' Does that mean 
advanced programmers are God?
  To learn how to make a tree, begin by sketching a picture of a 
tree on paper. Since N is the alphabet's middle letter, begin by 
writing the letter N, and put two arrows underneath it:
                   N


The left arrow is called the before-arrow; it will point to the 
names that come alphabetically before N. The right arrow is 
called the after-arrow; it will point to the names that come 
alphabetically after N.
                                                     For example, 
suppose your first topic is SUE. Since SUE comes alphabetically 
after N, put SUE at the tip of N's after-arrow:
                   N

                            SUE


                                                     Suppose your 
next topic is CAROL. Since CAROL comes alphabetically before N, 
put CAROL at the tip of N's before-arrow:
                   N

       CAROL                SUE


                                                     Suppose your 
next topic is ZELDA. Since ZELDA comes after N, we'd like to put 
ZELDA at the tip of N's after-arrow; but SUE's already stolen 
that position. So compare ZELDA against SUE. Since ZELDA comes 
after SUE, put ZELDA at the tip of SUE's after-arrow:
                   N

       CAROL                SUE

                                ZELDA


                                                     Suppose your 
next topic is ALICE. Since ALICE comes before N, look at the tip 
of N's before-arrow. Since CAROL's stolen that position, compare 
ALICE against CAROL; since ALICE comes before CAROL, put ALICE at 
the tip of CAROL's before-arrow:
                   N

       CAROL                SUE

  ALICE                         ZELDA


                                                     Suppose your 
next topic is JANE. Since JANE comes before N, look at the tip of 
N's before-arrow. Since CAROL's stolen that position, compare 
JANE against CAROL; since JANE comes after CAROL, put JANE at the 
tip of CAROL's after-arrow:
                   N

       CAROL                SUE

  ALICE     JANE                ZELDA



  If the next few topics are FRED, then LOU, then RON, then BOB, 
the tree looks like this:
                   N

       CAROL                SUE

  ALICE     JANE       RON      ZELDA

     BOB  FRED LOU


Look at the arrows that point down from N. N's before-arrow 
points to the group of names that come alphabetically before N 
(such as CAROL, ALICE, JANE, BOB, FRED, and LOU); N's after-arrow 
points to the group of names that come alphabetically after N 
(such as SUE, RON, and ZELDA). Similarly, CAROL's before-arrow 
points to the group of names that come alphabetically before 
CAROL (such as ALICE and BOB); CAROL's after-arrow points to the 
group of names that come alphabetically after CAROL (such as 
JANE, FRED, and LOU).
  Programmers treat the tree as if it were a ``family tree''. 
CAROL is called the parent of ALICE and JANE, who are therefore 
called CAROL's children. CAROL is called the ancestor of ALICE, 
JANE, BOB, FRED, and LOU, who are therefore called CAROL's 
descendants. The arrows are called pointers.
  To make the tree more useful, begin with ``N !'' instead of 
``N'' (so you can choose ``N'' as a topic later), and number the 
topics in the order they appeared: since SUE was the first topic, 
put ``1'' in front of SUE; since CAROL was the second topic, put 
``2'' in front of CAROL; since ZELDA was the third topic, put 
``3'' in front of ZELDA, like this:
                  N !

      2CAROL               1SUE

 4ALICE    5JANE      8RON     3ZELDA

    9BOB 6FRED7LOU


  To describe the tree to the computer, store this table in the 
computer's memory:
Topic                            Where the before-arrow 
pointsWhere the after-arrow points
0 N !                                    2                     1
1 SUE                                    8                     3
2 CAROL                                  4                     5
3 ZELDA                                  0                     0
4 ALICE                                  0                     9
5 JANE                                   6                     7
6 FRED                                   0                     0
7 LOU                                    0                     0
8 RON                                    0                     0
9 BOB                                    0                     0
That table represents the tree and is called the tree's 
representation.
                             The table's left column is in 
chronological order, but the other columns give information about 
alphabetizing. So a tree combines chronological order with 
alphabetical order: it combines the advantages of both. Adding a 
new topic to the tree is quick and easy (as in chronological 
order): just add the name to the bottom of the list, and adjust a 
few arrows. Using the tree to search for a topic is quick and 
easy (as in alphabetical order): just follow the arrows.
                             Like the alphabetical program, the 
program that creates and manipulates the tree uses the same 
subroutines 1000, 3000, 4000, and 5000 as the chronological 
program. To create the tree, change the main routine and 
subroutines 2000, 6000, and 7000. You must also add a new 
subroutine (8000). Here are those new routines:
The main routine T
All variables will be integers.            10 DEFINT A-Z
Allow 100 topics, data, etc.               20 DIM 
T$(100),D$(100),P(100,2)
Topic #0 is "N !".                         30 T$(0)="N !": 
P(0,1)=0: P(0,2)=0
The number of real topics is 0.            40 N=0
Ask the human for a topic.                 50 PRINT: PRINT "WHAT 
TOPIC INTERESTS YOU?": PRINT "(I
                                           F YOU'RE NOT SURE, 
TYPE A QUESTION MARK)": LINE INPUT  T$
Do what the human wishes.                  60 IF T$="?" THEN 
GOSUB 1000 ELSE GOSUB 2000
Go to another topic.                       70 GO TO 50

Subroutine 2000T: search through the database, to find the topic 
T$
Starting at 0, hunt for T$.                2000 I=0: GOSUB 8000
If absent, do 4000, else 3000.             2010 IF I=0 THEN GOSUB 
4000 ELSE GOSUB 3000
                                           2020 RETURN

Subroutine 6000T: insert the topic into the database
Increase the number of topics.             6000 N=N+1
Append new topic & its data.               6010 T$(N)=T$: 
D$(N)=D$: P(N,1)=0: P(N,2)=0
Make topic I1 point to it.                 6020 P(I1,J)=N
                                           6030 RETURN

Subroutine 7000T: delete the topic from the database
Make topic I1 (which was pointing to the vanishing topic) point 
to the vanishing topic's left child instead.
                                           7000 P(I1,J)=P(I,1)
A is the number of the vanishing topic. B is the number of the 
vanishing topic's right child.
                                           7010 A=I: B=P(I,2)
If the vanishing topic has a right child, make something point to 
that child.
                                           7020 IF B>0 THEN 
T$=T$(B): I=I1: GOSUB 8000: P(I1,J)=B
If the vanishing topic isn't topic N, move topic N to the gap 
left by the vanishing topic.
                                           7030 IF A<N THEN 
T$=T$(N): I=0: GOSUB 8000: P(I1,J)=A:
                                            T$(A)=T$: 
D$(A)=D$(N): P(A,1)=P(N,1): P(A,2)=P(N,2)
Decrease the number of topics.             7040 N=N-1
                                           7050 RETURN

Subroutine 8000T
Starting at position I, hunt for T$ in the database. If T$ is 
missing from the database, make I be 0; otherwise make I be the 
position of T$. Find the topic that points to T$. Make I1 be that 
topic's position. If the arrow pointing to T$ points left, make J 
be 1; otherwise make J be 2. Here's how to do all that:

If the topic is found, return.             8000 IF T$=T$(I) THEN 
RETURN
Compute a tentative J.                     8010 IF T$<T$(I) THEN 
J=1 ELSE J=2
Compute a tentative I1 and I.              8020 I1=I: I=P(I,J)
If pointer is not 0, hunt again.           8030 IF I>0 THEN GO TO 
8000
                                           8040 RETURN

                                          Disk-based database
                             All those database programs 
(chronological, alphabetical, and tree) put data into the RAM. 
When you turn off the power, the RAM forgets all the data!
  This superior program puts the database onto a disk instead of 
into RAM:
The main routine D
Prepare the variables.10 DEFINT A-Z: DIM PF$(2): Z$=MKI$(0)
Open the file and its fields.20 OPEN "INFO" AS 1 LEN=128: FIELD 
1, 44 AS TF$, 80 AS DF$, 2 AS PF$(1), 2 AS PF$(2)
Topics #1 and #2 are headers. Topic #2 should be "N !", and topic 
#1's left pointer should be N.
                30 IF LOF(1)=0 THEN N=2: LSET TF$="N !": LSET 
PF$(1)=Z$: LSET PF$(2)=Z$: PUT 1,2 ELSE GET 1,1: N=CV
                I(PF$(1))
Ask the human for a topic.40 PRINT: PRINT "WHAT TOPIC INTERESTS 
YOU?": PRINT "(IF YOU'RE NOT SURE, TYPE A QUESTION MARK)": PR
                INT "(IF YOU WANT TO END, TYPE THE LETTER X)": 
LINE INPUT T$
If the human wishes, do 1000.50 IF T$="?" THEN GOSUB 1000: GO TO 
40
If the human wishes, end.60 IF T$="X" THEN LSET PF$(1)=MKI$(N): 
PUT 1,1: CLOSE: END
Make TS$ resemble T$ but be 44 characters long (by adding blank 
spaces at the end).
                70 LSET TF$=T$: TS$=TF$
Find the topic. 80 GOSUB 2000
Go to another topic.90 GO TO 40

Subroutine 1000D: tell the human what topics are in the file
If just headers, say so.1000 IF N=2 THEN PRINT "I DON'T KNOW ANY 
TOPICS YET.": PRINT "MY MIND IS STILL BLANK.": PRINT "PLEA
                SE TEACH ME A NEW TOPIC.": RETURN
If file has topics, list them.1010 PRINT "I KNOW ABOUT THESE 
TOPICS:": FOR I = 3 TO N: GET 1,I: PRINT TF$: NEXT: PRINT "PICK 
ONE 
                OF THOSE TOPICS, OR TEACH ME A NEW ONE."
                1020 RETURN

Subroutine 2000D: search through the file, to find the topic TS$
Starting at 2, hunt for TS$.2000 I=2: GOSUB 8000
If absent, do 4000, else 3000.2010 IF I=0 THEN GOSUB 4000 ELSE 
GOSUB 3000
                2020 RETURN

Subroutine 3000D: the topic's in the file
Tell the human about the topic.3000 PRINT "HERE'S WHAT I KNOW 
ABOUT "T$":": PRINT DF$
Ask whether to change the info.3010 INPUT "DO YOU WANT TO CHANGE 
THAT INFORMATION";A$
If the human says yes, do 5000.3020 IF A$="YES" OR A$="Y" THEN 
GOSUB 5000
                3030 RETURN

Subroutine 4000D: the topic's not in the file
Say topic is not in the file.4000 PRINT "I DON'T KNOW ANYTHING 
ABOUT "T$"."
Request info about the topic.4010 PRINT: PRINT "TELL ME ABOUT 
"T$: PRINT "(IF YOU DON'T WANT TO TELL ME, TYPE THE LETTER X)": 
LI
                NE INPUT D$
If human wants, insert topic.4020 IF D$<>"X" THEN GOSUB 6000
                4030 RETURN

Subroutine 5000D: change the info
Agree to change the info.5000 PRINT "OKAY. I'VE ERASED THAT 
INFORMATION ABOUT "T$"."
Request new info.5010 PRINT: PRINT "TYPE WHAT YOU WANT ME TO KNOW 
ABOUT "T$: PRINT "(IF YOU WANT ME TO FORGET "T$", 
                TYPE THE LETTER X)": LINE INPUT D$
Change the info as requested.5020 IF D$="X" THEN GOSUB 7000 ELSE 
LSET DF$=D$: PUT 1,I
                5030 RETURN

Subroutine 6000D: insert the topic into the file
Increase the number of topics.6000 N=N+1
Let topic I1 point to topic N.6010 LSET PF$(J)=MKI$(N): PUT 1,I1
Append the new topic, at N.6020 LSET TF$=TS$: LSET DF$=D$: LSET 
PF$(1)=Z$: LSET PF$(2)=Z$: PUT 1,N
                6030 RETURN

Subroutine 7000D: delete the topic from the file
A is the number of the vanishing topic. P1 and P2 are the topic's 
pointers.
                7000 A=I: P1=CVI(PF$(1)): P2=CVI(PF$(2))
Make topic I1 (which was pointing to the vanishing topic) point 
to the vanishing topic's left child instead.
                7010 GET 1,I1: LSET PF$(J)=MKI$(P1): PUT 1,I1
If the vanishing topic has a right child, make something point to 
that child.
                7020 IF P2>0 THEN GET 1,P2: TS$=TF$: I=I1: GOSUB 
8000: LSET PF$(J)=MKI$(P2): PUT 1,I1
If the vanishing topic isn't topic N, move topic N to the gap 
left by the vanishing topic.
                7030 IF A<N THEN GET 1,N: PUT 1,A: TS=TF$: I=2: 
GOSUB 8000: GET 1,I1: LSET PF$(J)=MKI$(A): PUT 1,I1
Decrease the number of topics.7040 N=N-1
                7050 RETURN

Subroutine 8000D
Starting at position I, hunt for TS$ in the file. If TS$ is 
missing from the database, make I be 0; otherwise make I be the 
position of TS$.
Find the topic that points to TS$. Make I1 be that topic's 
position. If the arrow pointing to TS$ points left, make J be 1; 
otherwise make J be 2.
Here's how to do all that:

Start at position I.8000 GET 1,I
If the topic is found, return.8010 IF TS$=TF$ THEN RETURN
Compute a tentative J.8020 IF TS$<TF$ THEN J=1 ELSE J=2
Compute a tentative I1 and I.8030 I1=I: I=CVI(PF$(J))
If pointer not 0, hunt again.8040 IF I>0 THEN GO TO 8000
                8050 RETURN