Erschienen in 64'er Magazin, Ausgabe 08/1991 · Originaldatei: TRIKIS.TXT
Hinweis: Dies ist das an die Redaktion eingereichte Manuskript, nicht der gedruckte Endtext. Layout, Bildunterschriften, Korrekturen und Kürzungen der Redaktion können in der veröffentlichten Fassung abweichen.
Hätten Sie's gewußt?
Die Trickkiste
Interessante Tips und Kniffe, die nicht im Handbuch stehen
Alle diejenigen, die bisher der Meinung waren, ihren Computer wirklich bis aufs letzte Bit zu kennen, sollten aufmerken. Hier stellen wir Ihnen einige Kniffe und Tips vor, die es wirklich »faustdick hinter den Ohren haben«. Wir verraten Besonderheiten der Basic-Befehle, die nicht im Handbuch stehen. Das eine oder andere »Aha-Erlebnis« ist sicher auch für Sie dabei! Weiter hinten kommen dann noch »herkömmliche« Tips und Tricks, die jeder Einsteiger nützlich findet.
Alle Hinweise gelten, soweit nicht anders angegeben, für alle Acht-Bit Computer von Commodore, also neben C 64 und C 128 auch für VC 20, PLUS/4, C 16, C 116, PET 2001 und die alten Geräte der CBM-Reihe.
Strings PEEKen
Es stimmt wirklich. Dem Commodore 64 ist es egal, ob eine Zahl oder ein String zwischen die Klammern der PEEK-Funktion gesetzt wird. Sie können ohne weiteres PRINT PEEK(A$) schreiben, ohne eine Fehlermeldung zu erhalten. Auch PRINT POS(A$) besitzt diese syntaktische Immunität.
Der Wert, der zurückgegeben wird, hängt von der letzten numerischen Operation ab. Beispielsweise wirkt X=53280:PRINT PEEK(A$) wie PRINT PEEK(53280), ermittelt also die Farbe des Bildschirmrahmens.
Sie können auch ein Literal zwischen die Klammern setzen, so wie bei PRINT PEEK("HALLO"), allerdings ergibt dieser Ausdruck immer den Wert der Speicherzelle 0. Wenn Sie einen PEEK("STRING") dreimal in einer Zeile ausführen, beschwert sich das System dann aber doch mit einem ?OUT OF MEMORY ERROR. Aber was soll man auch anderes erwarten, wenn man Buchstaben dort verwendet, wo doch eigentlich Zahlen hingehören.
Die erste Dimension
Im Commodore-Basic sind bei dimensionierten Variablen elf Elemente Standard. Sie können ja zum Beispiel den Befehl PRINT A(10) oder A(10) = 19 verwenden, ohne vorher das Array A dimensioniert zu haben, und erhalten trotzdem keinen ?BAD SUBSCRIPT ERROR. Das funktioniert, weil Basic beim Start alle Arrays, egal ob String oder numerisch, mit dem Dimensionswert 10 (die Zählung beginnt bei Null, also elf Flemente) vorbelegt.
Das Kuriose dabei: Nachdem einer der beiden obigen Befehle abgearbeitet wuree, bewirkt DIM A(10) einen ?REDIM'D ARRAY ERROR, obwohl Sie doch noch gar kein Array dimensioniert haben!
Der nächste, bitte!
Der Befehl NEXT, der FOR..NEXT-Schleifen abschließt, wird gewöhnlich mit nur einer Variable versehen. Sie können ihn aber auch nutzen, um mehrere Schleifen gleichzeitig zu schließen. Die Folge NEXT A:NEXT B:NEXT C läßt sich einfach zusammenfassen zu NEXT A,B,C. Neben dem Zeitvorteil bei Eingabe und Ausführung des Programmes werden Programme so auch verkürzt.
Was ist CMD?
Vielleicht kennen einige von Ihnen schon den CMD-Befehl, der dazu dient, die Ausgabe auf ein neues Peripheriegerät, etwa den Drucker, umzuleiten. Klar, um ein Programmlisting auf dem Drucker auszugeben, schreiben Sie einfach: OPEN4,4:CMD4:LIST. Die Frage ist jetzt: Was bedeutet die Abkürzung CMD? Es ist ganz einfach: Die Bezeichnung steht für das englische Wort »CHANGE MAIN DEVICE«, also »Haupt-Gerät umschalten«.
Ein lästiger Nebeneffekt: Wird ein GET-Befehl ausgeführt, so werden alle bis dahin wirksamen CMD-Befehle wieder aufgehoben. Das kann, wenn man es nicht weiß, Ursache für unerwartete Programmierfehler sein.
Weiter, immer weiter
Der Befehl CONT kann nach einem Programmabbruch mit der RUN/STOP-Taste oder den Befehlen END oder STOP dazu verwendet werden, ein Programm an der Abbruchstelle fortzusetzen, wenn zwischendurch keine Änderungen am Programm durchgeführt oder Fehlermeldungen ausgegeben wurden. Was aber passiert, wenn CONT innerhalb eines Programmes zu finden ist? Ganz einfach: Dann wird CONT zur Endlosschleife. Übrigens unterscheiden sich die Befehle END und STOP wirklich nur dadurch, daß bei END die Meldung BREAK IN xxxx unterbleibt. Sonst sind diese Befehle identisch und austauschbar.
Verewigt in Silizium
Maler pflegen ihre Namen in die Ecke der Bilder zu schreiben, »Vandalen« sprühen ihre Namen auf Wände, ein jeder Simpel schreibt seinen Namen in jeden Winkel, Programmierer und Hardware-Designer verewigen sich im ROM. Wenn Sie einen C 128 besitzen, geben Sie doch einmal ein: SYS 32800,123,45,6 (leicht zu merken). Beim C 64 gibt es diese Art von Impressum leider nicht.
Wieviel ist ein Punkt wert?
Ja, wieviel denn? Nichts! Oder, besser gesagt: Null. Immer, wenn die Ziffer Null allein verwendet wird, kann man sie durch einen Punkt ersetzen. Basic führt Befehle mit dem Punkt sogar schneller aus als mit der Null. Anders gesagt,
10 POKE 53281,.:POKE 53281,1:GOTO 10
läuft schneller als die gleichbedeutende Zeile
10 POKE 53281,0:POKE 53281,1:GOTO 10
DATA-Tip
Nuller in DATA-Zeilen können auch einfach weggelassen werden. Das spart ein wenig Speicherplatz und Tipp-Arbeit. Statt
10 DATA 34,0,2,45,0,0,23,0,0,0,2
kann man auch schreiben:
10 DATA 34,,2,45,,,23,,,,2
Ebenso lassen sich die "" bei Leerstrings in DATAs einsparen. Bei Strings gibt es noch eine Besonderheit zu beachten: Sollen geSHIFTete Buchstaben in DATA Verwendung finden, müssen die Texte in Anführungszeichen gesetzt werden, da der Interpreter sie sonst in Tokens wandelt. Sonst können die Anführungszeichen wegfallen.
Inkompatible Zwillinge
Jeder Programmierer kennt den Befehl GOTO, der den Programmablauf an einer bestimmten Zeile fortsetzt. Wußten Sie, daß der Befehl GOTO bzw. GOSUB ohne eine Zahl dahinter so wirkt wie GOTO 0 bzw. GOSUB 0? Dies kann man nutzen, wenn es um jedes Byte geht, etwa bei Einzeilern. Außerdem kann GOTO in zwei separate Wörter getrennt werden: Also nicht GOTO 20, sondern GO TO 20. (Wenn Sie es nicht glauben, probieren Sie es aus! Auch wenn das im Englischen grammatikalisch eigentlich korrekter ist, wird GO TO so gut wie nie verwendet, und das aus gutem Grund. GO TO belegt nicht nur im Speicher zwei Bytes mehr (eines für das Leerzeichen, eines für das zusätzliche Token für TO), sondern ist auch gar nicht voll kompatibel zu seinem kompakten Bruder GOTO.
Beispielsweise ist gegen ON A GOTO 100, 200, 300 nichts einzuwenden, während ON A GO TO 100, 200, 300 nur einen ungläubigen ?SYNTAX ERROR provoziert. Mit dem GOTO, das ja direkt hinter IF verwendet werden darf, ist es das selbe: IF A=4 GOTO 100 macht seine Sache einwandfrei, IF A=4 GO TO 100 ist zum Scheiteren verurteilt. Der Befehl GOSUB darf nicht zerlegt werden.
GOTO auf Trab gebracht
Generell gilt, daß der Aufruf von Unterprogrammen mit GOSUB schneller ist als mit GOTO. Häufig benutzte Unterprogramm gehören an den Programmanfang, müssen dann allerdings zuerst mit einem GOTO umgangen werden. Beispiel: Die folgende Routine beginnt ab Zeile 2, das Hauptprogramm kann wegen Zeile 1 dennoch mit RUN gestartet werden:
1 GOTO 10
2 PRINT "BITTE TASTE DRUECKEN!"
3 POKE 198,0:WAIT 198,1:POKE 198,0
4 RETURN
10 hier beginnt das Hauptprogramm
Malnehmen für Könner
Auch bei Multiplikationen läßt sich ein Geschwindigkeitsgewinn erzielen, indem die größere der beiden Zahlen, die malgenommen werden sollen, vor den Stern gestellt wird. PRINT 3463 * 2 ist also schneller als PRINT 2 * 3463, obwohl mathematisch gleichbedeutend (kommutativ). Nicht nur aus Geschwindigkeitsgründen sollten Sie die Potenzfunktion soweit als möglich vermeiden. Geben Sie einmal ein PRINT 7^2, Sie werden sich wundern! Besser ist PRINT 7*7.
Einer fehlt!
Die Funktion MID$() benötigt drei Parameter, um aus einem String einen bestimmten Teil herauszuschneiden, oder nicht? Nein! Es genügen auch zwei Parameter. Wird der dritte Wert weggelassen, ergibt MID$() einfach alle Zeichen beginnend bei dem, das durch den zweiten Parameter angegeben wird. Der Befehl PRINT MID$("TESTPROGRAMM",5) gibt »PROGRAMM« aus. Diese Kurzform ist dann nützlich, wenn Sie ein RIGHT$ ausführen möchten, aber nicht wissen, wie viele Zeichen der Endstring enthalten soll, nur, ab wo im Quelltext er beginnt.
Übrigens steht im Handbuch, daß beide Parameter bei MID$ von 0 bis 255 liegen dürfen. Das ist verkehrt. Der erste Parameter darf nicht Null sein, sonst erscheint ein ?ILLEGAL QUANTITY ERROR.
Professionell Nachladen
Gewöhnlich hat das Nachladen eines Maschinenprogrammes von einem Basicprogramm aus mit dem Befehl LOAD "CODE",8,1 einen lästigen Nebeneffekt: Das Basicprogramm wird von vorn gestartet. Diesen Effekt vermeiden Sie, indem Sie stattdessen schreiben: SYS 57812 ("CODE"),8,1:POKE 780,0:SYS 65493. Kurz eine Erklärung: Der erste SYS-Befehl setzt die File-Parameter, also den Namen, die Geräte- und Sekundäradresse. POKE 780,0 sagt dem System, daß geladen, kein VERIFY ausgeführt werden soll. Der nächste SYS-Befehl schließlich ruft die LOAD/VERIFY-Routine auf.
Dieser Trick ist nur für Besitzer eines C 64 interessant, auf dem C 128 bzw. C 16 steht ohnehin der BLOAD-Befehl zur Verfügung.
Joker
Mit Hilfe der »Joker« »*« und »?« läßt sich die Directory-Ausgabe genauer spezifizieren. Um beispielsweise ein Directory zu erhalten, in dem nur PRG-Files enthalten sind, schreibt man einfach:
LOAD "$0:*=P",8
LIST
Sie können das P durch ein S, U oder R ersetzen, und erhalten dann alle SEQ, USR bzw. REL-Files.
Wenn Sie ein Programm laden wollen, aber nur den Anfang des Filenamens kennen, schreiben Sie
LOAD "FILENA*",8
Das wissen Sie schon. Wenn ein Filename mit dem Sternchen endet, erhält das DOS (Floppy-System) den Auftrag, File(s) zu bearbeiten, deren Name mit der Vorgabe vor dem Stern beginnt. Ebenso ist es möglich, unbekannte einzelne Zeichen im Namen durch das Fragezeichen zu ersetzen:
LOAD "FILENA?E",8
Aber wußten Sie schon, daß diese Spielereien auch beim Directory funktionieren? Beispielsweise wünschen Sie einen Ausdruck aller Files, die mit HAT beginnen und ein E als fünften Buchstaben haben:
LOAD "$:HAT?E*",8
LIST
Datenschutz
Jeder hat hin und wieder den Wunsch, ein Programm so auf Diskette abzuspeichern, daß nur er es wieder laden kann, sonst niemand. Hier sind zwei verschiedene Tricks, die es auch für den fortgeschrittenen Anwender schwer machen, ein Programm zu laden. Beide arbeiten auf allen 1541-kompatiblen Laufwerken.
Erstens, ein Basicprogramm läßt sich durchaus so speichern, daß es im Directory als SEQ oder gar als USR-File erscheint. Dazu hängen Sie nur den gewünschten Filetyp an den Filenamen an:
SAVE "BEISPIEL,S",8
oder
SAVE "BEISPIEL,U",8
Wenn Sie jetzt das Directory begutachten, werden Sie feststellen, daß aus Ihrem PRG-File im ersten Fall ein SEQ-File geworden ist, im zweiten Fall ein USR-File. Nun probieren Sie mal, das File mit
LOAD "BEISPIEL",8
wieder zu laden. Denkste! Ein ?FILE NOT FOUND ERROR erscheint, und die rote Floppy-Lampe blinkt. Das Programm kann nur auf die selbe Weise wieder geladen werden, in der es gespeichert wurde, also mit
LOAD "BEISPIEL,S",8
oder
LOAD "BEISPIEL,U",8
je nach Filetyp.
Noch gemeiner wird es, wenn Sie das Programm mit einem Nullbyte im Filenamen speichern:
SAVE CHR$(0)+"TESTNAME",8
Im Inhaltsverzeichnis erscheint der Name stark verstümmelt, zusammen mit einer völlig falschen File-Länge, so um die 10000 Blocks. Natürlich ist das File nicht wirklich so groß. Das Programm kann nun nur der laden, der den Kniff kennt:
LOAD CHR$(0)+"TESTNAME",8
Anders ist nichts zu machen!
Struktur ist alles!
Basic ist wirklich nicht die Sprache, für die sich Freunde von strukturierter Programmierung entscheiden - weit davon entfernt! Aber was bleibt dem Einsteiger auf dem C 64 anderes übrig als Basic? Dennoch soll hier ein Tip nicht fehlen, wie man Basicprogramme zumindest künstlich etwas besser strukturiert. Die folgenden Befehlszeilen sehen nicht besonders übersichtlich aus:
10 FORI=1TO20:FORJ=1TOI:A=4:GOSUB400:NEXTJ,I
Syntaktisch ist nichts gegen die Zeile einzuwenden. Wer Wert auf Struktur legt, schreibt stattdessen:
10 FOR I=1 TO 20
20 FOR J=1 TO I
30 A=4
40 GOSUB 400
50 NEXT J
60 NEXT I
Jedem Befehl wird eine eigene Zeile gegönnt. Jetzt wäre es schön, wenn man noch die Schleifen entsprechend einrücken könnte. Das Problem dabei ist nur, daß der Interpreter Leerzeichen am Anfang einer Zeile streicht. Dem helfen wir ab, indem wir einen Doppelpunkt an den Zeilenanfang stellen:
10 FOR I=1 TO 20
20 : FOR J=1 TO I
30 : A=4
40 : GOSUB 400
50 : NEXT J
60 NEXT I
Der Nachteil soll nicht verschwiegen werden: Dieser Programmteil wird nicht so schnell abgearbeitet, wie oben. Dafür ist er auch für fremde Programmierer einfach und übersichtlich zu durchschauen.
Vorsicht, Falle!
Eine Falle besonderer Art birgt der GET-Befehl, wenn er auf numerische Argumente angewandt wird. Etwa für eine Menüabfrage würde sich folgendes anbieten:
100 GET A
110 IF A=0 THEN 100
Ab Zeile 120 würde man dann je nach A in die einzelnen Menüpunkte verzweigen. Zeile 100 holt die gedrückte Taste nach A (es soll ja eine Zifferntaste gedrückt werden), in Zeile 110 wird diese Schleife weitergeführt, falls noch kein Tastendruck erfolgte.
Diese Konstruktion funktioniert, solange Sie nur Zifferntasten drücken. Sie bricht aber in sich zusammen, will sagen, ergibt einen ?SYNTAX ERROR, wenn ein unvorsichtiger Anwender stattdessen eine Buchstabentaste drückt. Sicher keine Auszeichnung für den Programmierer. Sie sollten GET daher grundsätzlich nur für Strings anwenden, die dann mit VAL in einen numerischen Wert gewandelt werden. Im Beispiel muß nur Zeile 100 geändert werden:
100 GET A$:A = VAL(A$)
Jetzt wartet das Programm auf Zifferntasten und steigt auch dann nicht aus, wenn Sie eine alphanumerische Taste drücken.
INPUT-Bug
Der INPUT-Befehl enthält leider einen Fehler. Die Prompts (Text in Anführungszeichen direkt nach INPUT) sollten nicht in die nächste Bildschirmzeile hineinreichen, da er sonst aufgrund eines Fehlers in den ROMs der älteren C 64-Modelle Teil der Eingabe wird.
Der Computer liest bei INPUT übrigens alles, was rechts vom Fragezeichen steht. Wenn sich also Grafik oder Text auf der selben Zeile rechts vom Fragezeichen befindet, wird dieser Bildschirminhalt zusammen mit den eingegebenen Daten gelesen und verursacht so ziemlich sicher Fehler. Stellen Sie vor INPUT also fest, daß der rechte Teil der Zeile gelöscht ist.
Der Code von Nichts
Basic-Programmierer verwenden die Funktion ASC() dazu, den ASCii-Code eines Strings zu ermitteln. Bei den Commodore-Rechnern hat ASC allerdings eine Schwäche: Sie ergibt einen ?ILLEGAL QUANTITY ERROR, wenn der String des Arguments leer ist. Verständlicherweise, denn ein Leerstring hat auch keinen Code. Dumm ist das nur, wenn beispielsweise ein File byte-weise gelesen und in ASCii-Codes zerlegt wird:
10 OPEN 2,8,2,"FILENAME,S,R"
20 GET#2,A$
30 A=ASC(A$)
Hier tritt in Zeile 30 eine Fehlermeldung auf, wenn in Zeile 20 ein Nullbyte gelesen wird. Der GET#-Befehl ergibt in diesem Fall nämlich einen Leerstring. Hier kann Abhilfe geschaffen werden, indem wir sicherstellen, daß die ASC-Funktion mit einem CHR$(0) gefüttert wird, wenn A$ leer ist. Dazu ändern wir Zeile 30 wie folgt:
30 A=ASC(A$+CHR$(0))
Ist A$ leer, ergibt die Addition mit CHR$(0) den gewünschten String: CHR$(0). Ist A$ nicht leer, stört die String-Addition nicht weiter, da ASC nur das erste Zeichen des Parameter-Strings berücksichtigt.
Alles relativ
Mit LOCATE positioniert man beim C 128 den Grafik-Cursor an eine Stelle des Hires-Bildschirms, DRAW zeichnet Punkte. Interessanterweise lassen sich beide Befehle auch relativ adressieren. Dazu wird ein Pluszeichen vor die Parameter gesetzt. LOCATE +20,+50 bewegt den Grafik-Cursor von seiner aktuellen Position um 20 Pixel nach rechts und 50 Pixel nach unten. DRAW 1,+40,+60 zeichnet gemessen von der aktuellen Position des Stiftes einen Punkt 40 Pixel weiter rechts, 60 Pixel weiter unten. Negative Werte führen zu Fehlermeldungen.
Alles Zufall?
Die Basic-Funktion RND liefert Pseudo-Zufallszahlen im Bereich zwischen 0 und 1. Setzt man N=RND(X), so sind die Werte N abhängig vom Argument X der Zufallsfunktion. Drei mögliche Erzeugungsarten sind vorgesehen:
X größer 0: Der genaue Wert des positiven Zahlenwertes X spielt keine Rolle, RND(2) und RND(1) ergeben die gleiche Zufallszahlenreihe, da hier ein fester Zahlenwert als »Keinzahl« (»Samen«) verwendet wird. Der neue Zufallswert wird nach einem einfachen Algorithmus aus dem alten gebildet. Der erste Samen wird nach dem Einschalten auf 0,811 635 157 gesetzt.
X = 0: Dieses Argument bewirkt, daß die Zufallszahlen abhängig vom Timer der CIA1 gebildet werden. Auch hier ist die erzeugte Zahlenreihe nicht wirklich zufällig.
X kleiner 0: Für negative Argumente ist die Zufallszahl eine Funktion des Arguments. Das heißt, daß hier bei jedem Aufruf eine neue Keimzahl gebildet wird. Bei der Verwendung der Systemzeit TI etwa wird stets in Abhängigkeit von TI ein neuer Samen gebildet: N=RND(-TI).
16 Funktionstasten abfragen
Mit einem genialen Trick lassen sich per Programm bis zu 16 Funktionstasten des C 64 abfragen. Wir kommen dabei ohne umständliche IF..THEN-Abfragen aus. Definieren Sie nur am Anfang Ihres Programms die Funktion
10 DEFFNA(X)=(X > 2)*(X < 7)*(((X-3-(X < 4)*4)*2)+(Y=0 OR Y=2))-(Y > 1)*8)
An entsprechender Stelle im Programm steht dann die Zeile
100 X=PEEK(197):Y=PEEK(653):IFFNA(X)=0 THEN 100
110 weiter im Programm
Wurde eine Funktionstaste gedrückt, macht der Computer mit Zeile 110 weiter. In X erhalten Sie nun bis zu 16 verschiedene Werte, die für folgende Kombinationen stehen:
(f 1), (f 3), (f 5), (f 7) allein
(f 2), (f 4), (f 6), (f 8) mit (SHIFT)
(f 9), (f11), (f13), (f15) mit (CBM)
(f10), (f12), (f14), (f16) mit (CTRL)
Das Eine oder das Andere, aber nicht beides
Gute Basic-Programmierer können durch die Verwendung der logischen Operatoren AND und OR ihre Programme verkürzen. Ein wichtiger Operator fehlt dem C 64 allerdings: Das ausschließende Oder (exclusive or, EOR). Bei AND ist das Ergebnis 1, wenn beide Operanden 1 sind. Bei OR erscheint die 1, wenn einer der beiden Operanden 1 ist. Was fehlt, ist die EOR-Verknüpfung, die eine 1 liefert, wenn genau ein Operand 1 ist, nicht aber beide.
EOR läßt sich aber mit AND und OR simulieren:
X = (A OR B) - (A AND B)
X ist das Ergebnis der bitweisen EOR-Verknüpfung von A und B.
Vergiß mein nicht!
Das Problem: In einem Basicprogramm soll der Wert einer Variable auch über den RUN-Befehl hinaus erhalten bleiben. Denken Sie an ein Basic-Spiel, bei dem der Highscore trotz Neustart mit RUN gespeichert werden muß. Die Lösung: Wir POKEn den Wert in eine unbenutzte Speicherzelle und holen ihn uns nach dem Start mit PEEK wieder. Das klappt bei ganzzahligen Werten von 0 bis 255. Soll ein Highscore in der Variable H (ganzzahlig, von 0 bis maximal 65535) gespeichert werden, kann er zunächst in High- und Lowbyte zerlegt werden:
200 HH=INT(H/256):HL=H-HH*256
Jetzt schreiben wir den Wert etwa in die unbenutzten Speicherzellen 701 und 702 und starten das Programm neu:
202 POKE 701,HL:POKE 702,HH:RUN
In der ersten Programmzeile lesen wir den Highscore aus:
10 H=PEEK(701)+256*PEEK(702)
Es tritt ein Problem auf: Nach dem Einschalten des Rechners stehen in 701 und 702 zufällige Werte, daher erhält die Variable HH bei ersten Start des Programms einen Zufallswert. Wir sollten daher dem Computer auch melden, daß sich gültige Werte in 701 und 702 befinden, etwa durch den speziellen Wert 123 in der Zelle 703, der dort nach dem Einschalten gewöhnlich nicht steht:
202 POKE 701,HL:POKE 702,HH:POKE 703,123:RUN
10 H=0 : IF PEEK(703)=123 THEN H=PEEK(701)+256*PEEK(702)
Sollte das Programm das erste Mal gestartet werden, erhält H den Wert 0, sonst den Wert vor dem Neustart in Zeile 202.
Gleichungen lösen
Das folgende kleine Programm löst Gleichungen!
10 DEF FN A (X)=
20 DEF FN B (X)=
30 A=1:S=1
40 FOR T=1 TO 9
50 FOR I=A TO 10^7 STEP S
60 IF FNA(I) > FNB(I) THEN 80
70 NEXT I
80 A=I-S: S=S*.1: NEXT T
90 PRINT"X =";X
In Zeile 10 und 20 müssen die linke und rechte Seite der Gleichung eingesetzt werden. Beispiel: Es soll die 27. Wurzel aus 5844 ermittelt werden, also X hoch 27 = 5844. Die Zeilen lauten:
10 DEF FN A (X) = X ^ 27
20 DEF FN B (X) = 5844
Nach dem Start mit RUN erscheint das richtige Ergebnis: X=1.37882068. Auch komplizierte Konstrukte wie (40+X)/40=40/X sind kein Problem:
10 DEF FN A (X) = (40+X)/40
20 DEF FN B (X) = 40/X
RUN
X=24.7213596
Hinweis: Die zu bearbeitenden Gleichungen dürfen keine quadratischen Gleichungen sein. Das Ergebnis muß positiv und kleiner als 10 Millionen (vgl. Zeile 50) sein. Ermittelt das Programm als Ergebnis -.1111111, so war die Aufgabe nicht lösbar.
Autostart
Wollten Sie schon einmal ein Basicprogramm schreiben, das sich nach dem Laden automatisch selbst startet? Hier ist die Methode, bei der Sie keinerlei Zusatzprogramm benötigen, ein »Kochrezept«. Sie brauchen weder Programmierkenntnisse in Basic oder gar Maschinensprache, noch ein Programm abzutippen. Fügen Sie lediglich zu dem Programm, das einen Autostart bekommen soll, in die allererste Zeile die beiden Befehle:
1 POKE 770,131:POKE 771,164
ein. Legen Sie jetzt eine formatierte Diskette mit genügend Platz ein und geben im Direktmodus in einer einzigen Zeile folgendes ein:
POKE 770,113:POKE 771,168:POKE 44,3:POKE 43,0:SAVE "FILENAME",8
Nach dem Speichern wird der Computere abstürzen, das ist normal. Schalten Sie das Gerät aus und wieder ein. Um nun den Autostarter zu laden, geben Sie ein:
LOAD "FILENAME",8,1
Wichtig ist der Zusatz ,1 nach dem normalen Ladebefehl. Stören Sie sich nicht daran, daß sich der Bildschirminhalt während des Ladens ändern wird, das Programm wird nach dem Laden automatisch starten. Wollen Sie nicht, daß man Zeichen auf dem Bildschirm sieht, während das Programm geladen wird, fügen Sie einfach vor die oben angegebenen vier POKEs den Befehl
PRINTCHR$(147):
ein. Dabei wird der gesamte Bereich ab Speicherzelle 768 gespeichert, Sie können dem Selbststarter also auch noch Nebenbedingungen mit auf den Weg geben, die nach LOAD ...,8,1 automatisch aktiv werden: Zum Beispiel
POKE 808,239 (RUN STOP verriegeln)
POKE 792,193 (RESTORE-Taste verriegeln)
POKE 775,191 (LIST verriegeln)
Diese Befehle müssen vor dem speziellen Speichern wie oben zu sehen eingegeben werden.
Die Notbremse
Fast so etwas wie das Gegenteil des vorangegangenen Tips: Leider enthält der C 64 »ab Werk« keinen eingebauten Reset-Taster. Dies wäre ein Knopf, mit dem der Rechner in den Einschaltzustand versetzt werden kann, beispielsweise wenn ein Programm abgestürzt ist. Für uns ist das aber kein Problem, man kann nämlich die RESTORE-Taste (rechts über der RETURN-Taste) in ihrer Funktionsweise ziemlich frei umdefinieren, beispielsweise einen Reset-Schalter daraus machen. Die beiden Befehle
POKE 792,226:POKE 793,252
erledigen das für uns. Wenn Sie jetzt die RESTORE-Taste (auch ohne RUN/STOP) betätigen, wird ein Reset ausgelöst, der C 64 wird in einen definierten Zustand zurückversetzt, die Einschaltmeldung erscheint. So werden beispielsweise verschiedene Arbeitsspeicherzellen mit sinnvollen Werten versorgt, die während des Betriebes verändert wurden. Dabei wird übrigens auch die Umbelegung von RESTORE widerrufen! Sie könnten nun mit einer Renew-Routine Ihr verlorenes Basicprogramm wiederholen.
Renew
Wie oft passiert es, daß man versehentlich den Befehl NEW eingibt und sich gleich darauf auf die Finger schlagen möchte: Studenlange Programmierarbeit scheint rettungslos verloren, weil das Basicprogramm dummerweise nicht gespeichert wurde. Den gleichen Effekt hat ein vorschneller Druck auf den Reset-Taster (vgl. vorher): Das Programm ist weg.
Aber halt, es ist nicht ganz verschwunden. Eigentlich ist es noch im Speicher des C 64, aber versteckt. Wenn nach dem Löschen noch keine weiteren Programmzeilen eingegeben wurden, helfen folgende Befehle, das Programm zu retten:
POKE 2050,8
SYS 42291
POKE 46,PEEK(35)-(PEEK(781) größer 253)
POKE 45,PEEK(781) + 2 AND 255
CLR
Wohlgemerkt dürfen vorher keine Basic-Zeilen eingegeben oder Variablen definiert worden sein (fatal wäre z.B. A=56), da sonst das Programm rettungslos verloren geht.
Diese oder verwandte Befehlskombinationen findet man oft in Basic-Erweiterungen. Der entsprechende Befehl heißt dann OLD oder RENEW, da er den NEW-Befehl rückgängig macht.
Seitenweise IF..THEN
Irgendwann kommt Ihnen einmal ein Programm unter, in dem viele Zeilen zum Beispiel so aussehen:
60 IF A=5 THEN B=7
70 IF A=6 THEN B=13
80 IF A=7 THEN B=-3
90 IF A=8 THEN B=6
Je nach Wert von A soll also B einen Wert zugewiesen bekommen. Aber so umständlich? Sagen wir, A ist eine Integervariable zwischen 5 und 21. Sie würden nach obigem Verfahren 17 IF..THEN-Befehle brauchen, um alle Möglichkeiten abzudecken; fast einen Bildschirm voll. Diese Befehle brauchen viel Platz und viel Programm-Rechenzeit; beides ist rar und teuer auf dem C 64. Die 17 Zeilen könnten aber durch einen einfachen Dreizeiler ersetzt werden. Am Beginn Ihres Programms müßte folgendes stehen:
10 DIM ZZ(17):FOR X=1 TO 17:READ ZZ(X):NEXT
12 DATA 7,13,-3,6, und so weiter
Der DATA-Befehl wird mit den Werten von B abhängig von A gefüllt. Später im Programm erfüllt dann jedes Mal, wenn er gebraucht wird, ein einfacher Zuweiser wie
60 B=ZZ(A-4)
die ganze Arbeit für uns. Die Zeilen ab 70 fallen weg. Da die Zahl in A zwischen 5 und 21 liegt, subtrahieren wir 4, um in den Bereich des ZZ-Arrays (1 bis 17) zu gelangen. Die Technik spart Speicherplatz und bringt einen deutlich spürbaren Zeitgewinn.
Raus aus dem Quote-Modus
Der Anführungszeichen-Modus (quote-mode) des C 64 ist sowohl eine nützliche wie auch eine frustrierende Angelegenheit. Wenn Sie schon programmiert haben, wissen Sie, wie angenehm es ist, Bildschirmbefehle wie Bildschirm löschen, Farbe ändern, Cursor bewegen einfach in PRINT-Befehle einzubauen. Aber Sie wissen auch, in welche »Schwulitäten« Sie kommen, wenn Sie editieren wollen, während Sie sich im Quotemodus befinden (nämlich nach der Eingabe eines Anführungszeichens mit SHIFT 2): Der Computer führt Ihre Cursorbewegungen nicht mehr aus, sondern vermerkt sie in Form von inversen Steuerzeichen innerhalb des Textes. Allerdings gibt es einige Möglichkeiten, dieser Betriebsart ohne Umstände zu entwischen:
Die RETURN-Taste schaltet grundsätzlich den Quote-Modus, den Einfüge-Modus und den Invers-Modus ab. Der Einfüge-Modus hat die gleichen Eigenschaften wie der Quote-Modus, allerdings werden hier auch Korrekturen mit (DEL) als Steuerzeichen (inverses T) dargestellt.
Ein manchmal nicht erwünschter Nebeneffekt der RETURN-Taste, nämlich die Übernahme der eingegebenen Zeile in den Speicher, tritt bei Druck auf (SHIFT RETURN) nicht auf. Sie können danach den Cursor wieder nach oben bewegen und Korrekturen vornehmen.
Beide Arten von (RETURN) bringen Sie in die nächste Bildschirmzeile. Um den Quote-Modus ohne »Platzverweis« zu stornieren, geben Sie einfach noch ein Anführungszeichen ein (SHIFT (2)) und drücken danach (DEL).
Diese Tricks arbeiten prima, wenn Sie ein Programm oder einen Text editieren, aber was tun, wenn man vom Programm aus einen zum Beispiel durch GET von Tastatur oder File eingeschalteten Anführungszeichen-Modus abschalten will? Der Computer befindet sich ja immer dann in dieser Betriebsart, wenn er ein Anführungszeichen auf dem Bildschirm ausgegeben hat. Um sicherzustellen, daß der Modus abgeschaltet ist, geben Sie einfach einen POKE 212,0 (auf dem C 64, bzw. POKE 203,0 auf einem C 16).
MSE als Kopierprogramm
Die einfachsten Ideen sind oft die besten. Die Eingabehilfe des 64'er-Magazins, der MSE, läßt sich als Kopierprogramm verwenden. Dazu laden Sie den MSE und starten ihn ganz normal. Vom MSE laden Sie das zu kopierende Programm und speichern es dann mit der Tastenkombination (CTRL S) auf eine andere Diskette oder Kassette. Diese Technik funktioniert mit allen Maschinen- oder Basicprogrammen und Datenfiles, die im Directory mit PRG vermerkt sind, allerdings lassen sich die meisten kopiergeschützten Programme damit nicht kopieren.
Lange Zahlenkolonnen
Oft werden zum Beispiel mit Schleifen wie dieser Zahlenlisten auf dem Schirm ausgegeben:
100 FOR I=1 TO 1000: PRINT AR(I): NEXT
Hier soll der Inhalt des 1000 Felder umfassenden Feldes AR() ausgegeben werden. Eine lange Folge von 1000 dahingeschmissenen Zahlen ist die Folge, ein Mensch wird kaum mitlesen oder kontrollieren können. Die CTRL-Taste verlangsamt zwar leicht, aber nicht genug. Wenn es Ihnen zu schnell geht, bauen Sie einfach einen Befehl wie WAIT 198,1,1:POKE 198,0 ein. Oben wäre das also:
100 FOR I=1 TO 1000: PRINT AR(I): WAIT 198,1,1:POKE 198,0: NEXT
Die Nummern erscheinen ganz normal auf dem Bildschirm, allerdings nur so lange, bis Sie eine Taste drücken. Dann hält der Computer so lange an, bis Sie noch eine Taste drücken. Es klingt seltsam, aber der dritte Parameter beim relativ unbekannten Befehl WAIT 198,1,1 sorgt dafür, daß der Computer so lange wartet, bis der Inhalt der Speicherzelle 198 (= Anzahl der bisher gedrückten Tasten) gerade ist. Wenn Sie eine Taste drücken (eine ungerade Anzahl), wartet der Computer so lange, bis Sie eine weitere Taste drücken. Diese Technik findet Anwendung, wenn Sie zum Beispiel mit PEEK einen großen Speicherbereich oder wie hier eine dimensionierte Variable durchsehen.
Weitere nützliche WAIT-Befehle
Da wir gerade den WAIT-Befehl behandelt haben, nutzen wir die Gelegenheit und führen Ihnen weitere äußerst trickreiche Anwendungen dieses Mauerblümchens vor. Der Befehl hat die Syntax
WAIT Adresse, Maske1 (, Maske 2)
und wartet, bis der Inhalt der angegebenen Speicherzelle ggf. exklusiv-oder (vgl. oben) verknüpft mit der zweiten Maske (falls eine angegeben ist) und danach und-verknüpft mit der ersten Maske einen Wert ungleich Null ergibt. Da sich nur diese Speicherzellen selbständig ändern, wird WAIT fast nur im Zusammenhang mit Ein-/Ausgabe-Adressen verwendet.
Ein Beispiel: Beim Commodore 64 findet sich in Speicherzelle 653 die Information, welche der Taste(n) (SHIFT), (CBM) und/oder (CTRL) gedrückt ist/sind. Bit 2 (Wertigkeit 4) dieser Zelle wird genau dann auf 1 gesetzt, wenn die CTRL-Taste gedrückt wird. Wollen Sie in Ihrem Programm darauf warten, daß der Anwender die CTRL-Taste drückt, geben Sie einfach den Befehl
WAIT 653,4
Man kann auch den Befehl geben, der Computer soll so lange warten, bis die CTRL-Taste (falls sie bei Erreichen des WAIT-Befehles denn gedrückt war) losgelassen wurde:
WAIT 653,4,4
ist die einfache Lösung. Für die SHIFT-Taste schreiben Sie statt der 4 eine 1 oder eine 2 für die Commodore-Taste. Mit Hilfe der SHIFT-LOCK-Taste können wir somit in jedes Basic-Spiel eine Pause-Funktion einbauen: Setzen Sie einfach in die Hauptschleife des Spieles (z.B. Bewegung der Spielfigur) den Befehl
WAIT 653,1,1
Das Spiel kann durch Einrasten der Taste SHIFT LOCK gestoppt werden, nach dem Entrasten geht es weiter.
Die Zelle 197 enthält einen speziellen Code der momentan gedrückten Taste oder die 64, wenn keine Taste gedrückt wird. Also können wir mit
WAIT 197,63
darauf warten, daß irgend eine Taste gedrückt wird, und mit
WAIT 197,64
darauf warten, daß alle Tasten losgelassen werden.
Wie bei allen Tricks dieser Rubrik spielt es auch hier keine Rolle, daß Sie die Kniffe verstehen, Sie sollten lediglich wissen, wie man sie anwendet, sozusagen das »Kochrezept«.
Die eingebaute Uhr des C 64 arbeitet mit den Speicherzellen 160 bis 162. Das machen wir uns zunutze, indem wir mit WAIT eine Pause von vorgegebener Länge erzeugen. Erst setzen wir die Uhr auf Null, dann warten wir, bis eine bestimmte Zeit vergangen ist, bis also ein bestimmter Wert im Uhrenregister steht. Die folgende Befehlsfolge erzeugt eine Zwangspause von 0,5 Sekunden:
POKE 162,0:WAIT 162,32
Die folgenden beiden gleichwertigen Zeilen erzeugen eine Wartezeit von 4-4/15 Sekunden:
POKE 161,0:POKE 162,0:WAIT 161,1
oder
TI$="000000":WAIT 161,1
Unverständliche Fehlermeldungen
Es gibt drei Fälle, da erscheinen nach der Eingabe fast aller Basicbefehle Fehlermeldungen, die sich aber nicht erklären lassen, weil der Befehl völlig korrekt war.
Im ersten Fall reagiert der C 64 auf jede Eingabe mit einem ?FORMULA TOO COMPLEX ERROR, Befehle werden überhaupt nicht mehr ausgeführt. Meistens ist die Ursache ein abgestürztes Programm oder ein fehlerhafter POKE, der den Computer scheinbar lahmlegt. Um diesen Effekt abzustellen, reicht ein
POKE 24,0
Der zweite Fall: Der Rechner reagiert auf viele Eingaben nur noch störrisch mit ?SYNTAX ERROR. Das liegt häufig daran, daß eine falsche Zahl in Speicherzelle 2048 den Basic-Speicher »verschmiert«. Mit
POKE 2048,1
können Sie diesen unangenehmen Effekt gar selbst provozieren. Treiben Sie damit Freunde und Bekannte zum Wahnsinn, denn denen wird es jetzt nicht mehr gelingen, Programm zu editieren oder mit RUN zu starten. Im Regelfall wird diese Situation aber nicht künstlich herbeigeführt, sondern entsteht durch einen Unfall. Wie kann dann die volle Funktionsfähigkeit des Computers ohne Programmverlust wiederhergestellt werden? Durch einen einfachen
POKE 2048,0
klappt alles wieder wie gehabt.
Drittens: Sie haben ein Maschinenprogramm absolut geladen, also mit dem Befehl LOAD "NAME",8,1. Solche Programme sind oft Hilfsprogramme und lassen sich beispielsweise mit SYS 49152 starten. Den Versuch, Variablen anzulegen oder Programme einzugeben oder zu starten quittiert der Computer allerdings gnadenlos mit einem ?OUT OF MEMORY ERROR, der einfach nicht verschwinden will. Abhilfe schafft ein einfacher NEW-Befehl, der zwar dem Maschinenprogramm nicht weh tut, aber das im Speicher stehende Basicprogramm löscht. Dieses holen Sie sich dann ggf. mit dem oben vorgestellten RENEW-Trick oder einem entsprechenden Hilfsprogramm zurück.
Schnelles Löschen von Zeilen
Leider fehlt dem Basic 2.0 des C 64 ein DELETE-Kommando, mit dem gezielt Zeilenbereiche eines Basicprogramms gelöscht werden können. Überflüssig zu erwähnen, daß das Löschen von vielleicht 40 oder 50 Zeilen sehr anstrengend und langweilig sein kann (Eingabe der ersten Zeilennummer, RETURN, Eingabe der zweiten Zeilennummer, RETURN, Eingabe der dritten Zeilennummer, RETURN, Eingabe der vierten Zeilennummer, RETURN, und immer so weiter). Zwar existieren Hilfsprogramme für diesen Zweck, aber wir wollen zeigen, wie es ganz einfach und effektiv geht.
Eine Lösung wäre ein Einzeiler, der die erforderlichen Nummern einfach auf den Schirm schreibt, wie
FOR I=3000 TO 3200 STEP 10:PRINT I:NEXT
Diese Zeile listet 20 Nummern im Bereich zwischen 3000 und 3200 (Schrittweite 20) auf dem Schirm. Um diesen Bereich zu löschen, tippen Sie einfach auf jeder Nummer RETURN. Wenn Ihr Programm nicht mit der Schrittweite 10 geschrieben wurde, fehlen vielleicht einige Zeilen, dann müssen Sie die Schrittweite STEP verändern. Glücklicherweise geht es noch simpler: Geben Sie erst einmal POKE 774,0 ein. Dieser Befehl schaltet den LIST-Befehl so, daß er nur die Zeilennummern zeigt (ausprobieren!). Jetzt holen wir uns den gewünschten Bereich mit einem einfachen
LIST 3000 - 3200
auf den Schirm und löschen mit RETURN jede Zeile. Danach schalten wir mit POKE 774,26 wieder den Normalbetrieb von LIST ein (oder RUN/STOP-RESTORE drücken).
LIST in Basicprogrammen
Normalerweise ist es nicht möglich, den LIST-Befehl innerhalb von Basicprogrammen zu verwenden, da der C 64 die Bearbeitung des Programms nach dem LIST-Befehl stoppt. Mit einem kleinen Trick ist es aber trotzdem möglich. Das folgende Beispiel listet innerhalb des Programms die Zeile 10.
10 POKE768,61:SYS42980,LIST10:POKE768,138
20 WAIT198,1: POKE198,0: PRINT"WEITER": GOTO10
Natürlich können Sie in Zeile 10 anstelle des LIST 10 auch zum Beispiel LIST 10- oder LIST 400-500 usw. schreiben. Vergessen Sie nicht das Komma nach dem SYS-Befehl!
Vorgaben
Viele Programmierer verwenden einen Befehl wie den folgenden, wenn Sie vom Anwender eine Eingabe erwarten und ihm schon eine mögliche Antwort vorgeben wollen:
INPUT"SIND SIE SICHER(2 SPACES)J(3 LEFT)";A$
Hier wird die Frage gestellt: SIND SIE SICHER? zusammen mit einem »Default«. Ein Default ist eine Vorgabe, in diesem Fall die Antwort »J«, die dem Programm übergeben wird, wenn der Anwender nur RETURN drückt, ohne etwas einzugeben. Dieser Trick funktioniert meistens ohne weiteres, die Cursor-Steuer-Kommandos sorgen dafür, daß sowohl die Vorgabe »J« (Sie hätten ebenso gut »N« schreiben können) wie auch das Fragezeichen, das der INPUT-Befehl selbst erzeugt, auf dem Bildschirm an der richtigen Stelle stehen.
Sie erkennen das Problem: Was tun, wenn die Länge des Defaults vorher nicht bekannt ist? Wenn die Vorgabe in einer Variable steht? Dann behelfen Sie sich am besten so:
PRINT"PROMPT ";X;:POKE211,6:INPUTX
Hierbei meint »PROMPT« den Abfrage-Text, zum Beispiel »Sind Sie sicher«. Der Befehl POKE 211,6 bewirkt, daß der Cursor in die 6. Bildschirmspalte gesetzt wird. Sie müssen je nach Länge des Prompts diesen Wert variieren (hier »PROMPT« = 6 Zeichen, daher 6). Verwenden Sie diese Technik mit einer String-Variable anstelle von X, schreiben Sie zwei Leerzeichen nach dem Prompt anstelle des einen.
Kommas im INPUT-Befehl
Nochmal INPUT: Der INPUT-Befehl, mit dem der C 64 ausgerüstet ist, hat - neben anderen Schwächen - einen Nachteil: Man kann keine Kommas eingeben. Ein Beispiel:
10 INPUT"TEXT";T$
20 PRINT"ES WAR";T$
Geben Sie hier in Zeile 10 einen Text ein, der Kommas oder Doppelpunkte enthält, so wird sich der Rechner mit einem ?EXTRA IGNORED beschweren und - wie beim folgenden PRINT-Befehl zu sehen ist - den Teil nach dem Komma bzw. Doppelpunkt gnadenlos abtrennen. Abhilfe: Ein Anführungszeichen, eingegeben vor dem Text. Dieses geht nicht in die Variable T$ ein, sorgt aber dafür, daß Sie in der Eingabe alle Zeichen verwenden dürfen (ausgenommen sind natürlich weitere Anführungszeichen).
Fehlerkanal im Direktmodus, Teil I
Die rote Fehler-LED der Floppy blinkt hektisch, ein Fehler ist aufgetreten. Aber welcher? Leider kann man normalerweise im Direktmodus nicht den Floppy-Fehlerkanal auslesen, das ist wegen dem dazu notwendigen INPUT#-Befehl nur innerhalb von Basic-Programmen möglich. Falls sich ein wichtiges Programm im Speicher befinden, das Sie nicht überschreiben wollen, stehen Sie jetzt ohne folgenden Trick ganz schön »auf dem Schlauch«.
Unter Zuhilfenahme einiger Maschinensprache-Systemroutinen des Computers (wie das funktioniert, müssen Sie nicht verstehen, Hauptsache, es klappt) gelingt es uns, auch im Direktmodus Dateien, zum Beispiel den Fehlerkanal zu lesen. Dazu öffnen wir erst den Kanal wie gewohnt mit
OPEN 15,8,15
Dann wird - im Direktmodus - folgende Zeile eingegeben:
FOR X=0TO40: POKE781,15: SYS65478: SYS65487: SYS65490: SYS65484: IF ST= 0 THEN NEXT
Es erscheint die Meldung, zum Beispiel
26, WRITE PROTECT ON,18,01
Danach wird (falls nicht mehr benötigt) der Kanal wieder geschlossen.
CLOSE 15
Dieser Trick klappt immer dann, wenn im Direktmodus eine Datei gelesen werden soll. Der Befehl SYS 65490 sorgt für die Ausgabe auf dem Bildschirm. Sie müssen ggf. nur nach dem POKE 781, die Filenummer des geöffneten Files (hier: 15) einsetzen. Beispielsweise listet folgendes »Programm«, das allerdings nur im Direktmodus läuft, eine Datei auf dem Drucker:
OPEN 1,8,2,"NAME DER DATEI,S,R"
OPEN 2,4
FOR X=1 TO 10000000: POKE 781,1: SYS 65478: CMD 2: SYS 65487: SYS 65490: SYS 65484: IF ST=0 THEN NEXT
CLOSE 1:CLOSE 2
Nach der Übertragung kann man mit
PRINT X
die Anzahl der gedruckten Zeichen erfragen.
Fehlerkanal im Direktmodus, Teil II
Haben Sie die obige Methode schon ausprobiert? Es geht auch einfacher: Wenn es dem Computer nicht »paßt«, daß wir im Direktmodus den INPUT#-Befehl anwenden, dann müssen wir ihm eben »vorgaukeln«, daß er sich im Programm-Modus befindet. In den Speicherzellen 57 und 58 steht während des Ablaufs eines Basicprogramms die Zeilennummer der gerade bearbeiteten Basic-Zeile, im Direktmodus ein spezieller Code. Schreiben wir direkt vor dem INPUT#-Befehl eine Null in diese Zellen, dann denkt der Computer, er befindet sich im Programm. Er meckert dann nicht bei der Abfrage des Fehlerkanals:
POKE 57,0:POKE 58,0:OPEN 1,8,15:INPUT #1,A,B$,C,D:PRINTA;B$;C;D: CLOSE 1
Die beiden POKEs haben keine Nebenwirkungen, sie werden automatisch sofort am Zeilenende bei CLOSE 1 wieder korrigiert.
Directory ohne Programmverlust
Häufig möchte man das Inhaltsverzeichnis einer Diskette in den Speicher bringen und listen, ohne das dabei im Speicher befindliche Programm zu löschen. Haben Sie nicht gerade eine Erweiterung wie DOS 5.1 zur Hand, hilft folgender Kniff:
POKE 44,PEEK(46)+1
Der Basic-Speicher wird auf einen freien Speicherplatz umgestellt. Jetzt können Sie wie gewohnt das Directory mit LOAD "$",8 laden und mit LIST ansehen. Mit
POKE 44,8:CLR
gelangen Sie dann wieder ins normale Programm zurück. Mit dieser Methode lassen sich auch andere Basic-Programme ohne Verlust des Hauptprogramms listen, allerdings nicht editieren, verändern oder starten.