Altair BASIC
1975 januárjában a Popular Electronics magazin bemutatta az Altair 8800 típusú számítógépet. A számítógépet 439 dolláros áron kit készletként (a felhasználónak otthon kellett összeforrasztania a gépet) árulták, de kb. másfélszeres áron (621 dollár) összeszerelve is meg lehetett vásárolni. A gépben az Intel 8080-as processzora volt, alapkiépítésben 256 byte RAM-ot tartalmazott. Szoftver viszont nem volt hozzá... PoviSoft-ot ihlette meg, hogy interneten megtalálható a BASIC disassemblált kódja és készített Enterprise-verziót. Ugyan az Enterprise-ban Z80-as processzor "dobog", ez elvileg nem kell, hogy problémát okozzon, hiszen gépi kód szintjén felülről kompatibilis az Intel 8080-nal (az Intel-ből kivált mérnökök tervezték a Z80-at). A gyakorlat mást mutatott: a Z80 processzor másképp kezeli a paritás jelzőbitet, mint az Intel 8080, ez okozott némi galibát átírásnál. |
Konfigurálás
A BASIC sikeres betöltése után, a terminálon - esetünkben a képernyőn - megjelenik az első kérdés: MEMORY SIZE?
A kérdésre bájtban kell megadni a rendelkezésre álló memória méretét. (A BASIC 8K-s verziójában itt elrejtettek egy easter egg-et: ha 'A'-t nyomunk válasznak, a "WRITTEN FOR ROYALTIES BY MICRO-SOFT" üzenet jelenik meg.) Ha nem írunk be semmit, csak ENTER-t nyomunk, a program "kideríti", mekkora RAM-unk van.
Sajnos két hibalehetőség is van:
1. Több memóriát írunk válasznak, mint amennyi valójában van.
Mivel a program nem végez ellenőrzést, hogy valóban van-e akkora RAM-unk, mint amennyit válasznak beírtunk, a veremmutató nem létező tárterületre fog mutatni, aminek előbb-utóbb szép kis fagyás lesz a vége.
2. A gépben 64kB RAM van, és csak ENTER-t nyomunk.
Ez egy bug. A memória méretének kiderítésekor a program egy ciklusban növelt pointer által mutatott területre próbál írni egy bájtot a memóriába, egészen addig, amíg a visszaolvasott érték nem egyezik az előzőleg beleírt értékkel (vagyis olyan területre értünk, ahol nincs RAM). A ciklusból viszont kimaradt a mutató értékének a vizsgálata, így a RAM tetejét elérve (ekkor 0xFFFF az értéke) a következő lépésben túlcsordulás lesz, a pointer a RAM aljára fog mutatni, majd szépen felülírja saját magát a program, és lefagy.
Jó kérdés, vajon véletlenül maradt-e benne ez a bug a programban, vagy tudatosan spóroltak így öt bájtot a mutató ellenőrzésének elhagyásával? Akkoriban ugyanis elképzelhetetlennek tűnt, hogy bárkinek is 64kB RAM-ja legyen. Először is, megfizethetetlen lett volna, több, mint 4000$-ba került ennyi memória 1975-ben, másrészt pedig fizikailag sem lehetett volna megvalósítani: egy bővítőkártyán összesen 4kB RAM volt elérhető akkoriban, ebből 16 db-ra lett volna szükség, azonban a gépben csak 15 szabad bővítőhely volt, miután a 16. hely foglalt volt a CPU-kártya számára. Véleményem szerint azonban ez egyszerű bug, hiszen a 4.0-ás verzióban már javították ezt a hibát.
Miért volt szükség erre a kérdésre, ha a program egyébként is ki tudta deríteni a rendelkezésre álló RAM méretét? Azért, mert a válaszként kisebb számot is írhattunk, mint amennyi RAM telepítve volt a gépbe. Ekkor garantálva volt, hogy a maradék tárterületet (a RAM tetejét) nem írja felül a BASIC a működése során. Ez azért volt jó, mert a BASIC betöltése előtt ide saját rutint is elhelyezhettünk, amit aztán a BASIC-ből is meg lehetett hívni.
A rendelkezésre álló memória beállítása után megjelenik a második kérdés: TERMINAL WIDTH?
Itt a terminálon (teletype-on) egy sorban elférő karakterek számát kell megadni, alapértelmezett esetben (ha nem írunk be semmit, csak ENTER-t nyomunk) az értéke 72. Enterprise-on célszerű 78-at megadni, hisz a képernyőn ennyi karakter fér el egy sorban.
Végül az utolsó kérdés: WANT SIN?
Itt eldönthetjük, hogy szükségünk van-e a szinusz- RND és négyzetgyök-függvényekre. Ha nem akarjuk azokat használni, akkor a BASIC felszabadítja a rutinok által lefoglalt tárhelyet, így 246 bájttal több szabad RAM-mal fogunk rendelkezni. Ebben az esetben ha mégis megpróbálnánk hívni a fenti függvények egyikét, akkor érvénytelen függvényhívás hibaüzenetet fogunk kapni.
A 4K BASIC (3.2-es verzió) korlátai
Mivel a programnak bele kellett férnie 4kB-ba úgy, hogy még maradjon elegendő hely a BASIC forráskódnak, a változóknak, és a veremnek is, egy sor kompromisszumot kellett meghozni, ami korlátozta a program használhatóságát.
Nagybetűk használata
A parancsok és változók neveit csak nagybetűs írással lehet megadni. Tehát a PRINT 2+2 parancs működik, de a print 2+2 már szintaktikai hibát generál. A BASIC 4.0-ás verziója (8K változat) már elfogadja a kisbetűs írást is (kivéve a WANT SIN? kérdésre adandó választ, - ez vélhetőleg bug).
Kétbetűs hibaüzenetek
A helytakarékosság miatt minden hibaüzenet két karakterből állt. (Pl.: SN = szintaktikai hiba; RG = RETURN GOSUB nélkül; /0 = osztás nullával stb.) Így, az összesen 12 darab hibaüzenet elfér egy 24 bájtos táblázatban.
Rövid változónevek
A változók nevei egy, vagy két karakterből állhatnak. Az első karakternek betűnek kell lennie (A..Z), a második - opcionális - karakter pedig csak szám (0..9) lehet. Így összesen 286 érvényes változónév érhető el. A 8K BASIC már elfogadja a hosszú változóneveket (arra kell csak figyelni, hogy ne tartalmazzon foglalt szót, pl.: a BEND már nem jó), de csak az első két karaktert veszi figyelembe. Vagyis a RETEK és a REPA ugyanazt a két változót jelenteti (ez a "feature" a C64-eseknek ismerős lehet...).
Sztringek hiánya
A 4K BASIC nem ismeri a string típusú változót. A sztringek és a sztring-kezelő függvények (pl.: LEN, LEFT$, RIGHT$ stb.) a BASIC 8K-s verziójától érhetők el.
Nincs LOAD és SAVE parancs
Mivel akkoriban a teletype és a lyukszalag író/olvasó berendezés ugyanazon a soros porton kommunikált, a program mentése úgy történt, hogy be kellett gépelni a LIST parancsot, majd még az ENTER leütése előtt a soros port kimenetét a teletype helyett a lyukszalag-íróra kellett átállítani. Így ahelyett, hogy a programlista kinyomtatásra került volna, egy üres lyukszalagra lyukasztódott.
A CLOAD és CSAVE (Casette LOAD és Casette SAVE) parancsok a 8K BASIC-ben jelentek meg, ezzel magnószalagra lehetett kimenteni, illetve betölteni a BASIC programot. Az Enterprise verzióban azonban nem ezek a parancsok szolgálnak a programok kimentésére / betöltésére (lásd később).
Lassabb lebegőpontos rutinok. A 8K-s verzió gyorsabb, mert 40 százalékkal gyorsabb lebegőpontos rutinokkal dolgozik.
A legnagyobb használható sorszám a 65529
Ez nem is igazán korlát (hiszen senki nem akart hatvanezer soros programot írni - el se fért volna a memóriában), inkább csak érdekesség. A BASIC programok sorszáma kétbájtos egészként vannak eltárolva, így elvileg 65535 lehetne a legnagyobb elérhető sorszám, azonban az csak 65529, mert így rövidebb és egyszerűbb kódot lehetett írni. Érdekes módon ez a korlát még a x86-on futó GW-BASIC-ben is benne van.
Szerkesztés a BASIC-ben
A szerkesztés nem a ma megszokott módon történik (A "teljesképernyős szerkesztés" akkoriban még ismeretlen fogalom volt, így nincsenek kurzormozgató billentyűk sem.), hanem egy kicsit körülményesebb. Az aktuális sor törlése a kukac "@" karakterrel lehetséges. Ekkor a kurzor a következő sor elejére kerül, és az addig begépelt sor törlődik a bufferből. Ha csak karakterenként szeretnénk visszatörölni a sorban, akkor ezt ERASE billentyűvel lehet megtenni.
A "szerkesztési" lehetőségek ezzel ki is merültek, így mindenképen célszerű programjainkat inkább külső szerkesztővel készíteni / javítgatni (akár a WP is jobb erre), hisz a programokat szöveges formában fogjuk tárolni. A szöveges állománnyal szemben támasztott egyetlen kritérium: a forráskód sorvégi lezáró jelnek CR/LF-nek, vagy CR-nek kell lenni! (Ellenkező esetben az utolsó sort nem olvassa be a BASIC.)
Az Enterprise verzió ki lett egészítve forrásfájl betöltő és kimentő paranccsal, ezek az F1 és F2 billentyűvel érhetők el (használja a FILE bővítést). A 8K verzió CLOAD és CSAVE parancsai ki lettek iktatva - nem csinálnak semmit. A 4K verzióban elérhető RAM 16kB.
Az abszolút retro-érzés kedvéért a CTRL+P gomb megnyomásával válthatjuk a kimenetet a nyomtató és a monitor között.
A STOP megnyomásával megszakítható a futtatott BASIC program. (Hatása megegyezik a CTRL+C billentyűkombináció megnyomásával.)
A BASIC-ből való kilépésre az F8 billenntyű szolgál. Nem kér megerősítést, óvatosan a használatával!
Szintaxis
A BASIC interpreter kétféle üzemmódban működik: parancs üzemmódban, vagy program üzemmódban. Azt, hogy a melyik üzemmódban értelmezi a bevitt sort az interpreter, az az adott sor első nem szóköz karakterétől függ. Ha ez szám, akkora a BASIC úgy tekinti, hogy programsort vittünk be, és elhelyezi a memóriába (ha van már ilyen sorszámú sor, az felülíródik). Ha az első karakter nem számjegy, akkor parancsnak értelmezi és rögtön végrehajtja. Az interpreter a legtöbb BASIC utasítást parancs- és program üzemmódban is végrehajtja.
Az egyes BASIC programsorok - növekvő sorszám szerint rendezve - követik egymást a memóriában. Minden sor előtt egy 2 byte-os mutató áll, amelyik a következő sor elejére (pontosabban az azt megelőző mutató első byte-jára) mutat. Ezt követi a sorszám 2 byte-on. A programsorban előforduló BASIC alapszavakat egyetlen byte-on tárolja. Ennek a byte-nak az értékét az illető alapszó tokenjének hívjuk. A " £ $ % ( ) , : ; jeleket a megfelelő ASCII kóddal ábrázolja. Az idézőjelek közötti szövegkonstansokat, a REM utasításban szereplő karaktereket ugyancsak ASCII kódjukkal ábrázolja. A programsorok végét egy 0 byte jelzi.
Foglalt szavak
4k verzió:
ABS | CLEAR | DATA | DIM | END | FOR |
GOSUB | GOTO | IF | INPUT | INT | LET |
LIST | NEW | NEXT | READ | REM | |
RESTORE | RETURN | RND | RUN | SGN | SIN |
SQR | STEP | STOP | TAB | THEN | TO |
USR |
8k verzió:
Az összes előbb felsorolt szó, továbbá az alábbiak:
ASC | AND | ATN | CHR$ | CLOAD | CONT |
COS | CSAVE | DEF | EXP | FN | FRE |
INP | LEFT$ | LEN | LOG | MID$ | NULL |
ON | OR | NOT | OUT | PEEK | POKE |
POS | RIGHT$ | SPC | STR$ | TAN | VAL |
WAIT |
Konstansok
A 4K verzióban csak valós (lebegőpontos) számkonstansokat használhatunk.
A valós számkonstansok egymás utáni összetevői a következők lehetnek: előjel, egészrész, tizedespont, törtrész, kis vagy nagy E betű, kitevő. Az egészrész és törtrész decimális számjegyek sorozata. Ha az előjelet elhagyjuk, a szám pozitív lesz. A számokat megadhatjuk tizedes és hatványkivevős alakban is. A szám első hét számjegye szingifikáns. A legnagyobb ábrázolható szám: 1.70141E+38. A legkisebb, még ábrázolható pozitív szám 1^-38.
A számkonstansok megjelenítésének szabályai:
Példák helyes számkonstansokra:
Szám: Kiírt alak: +1 1 -1 -1 6523 6523 06523 6523 1E20 1E+20 -12.3456E-7 -1.23456E-06 1000000 1E+06 0.1 .1 .001 1E-03 .000123 1.23E-04
A 4K verzióban szövegkonstansokat csak a PRINT utasítás paramétereként használhatunk. Ezen konstans maximális hosszát csak az köti meg, hogy a képernyőről legfeljebb 78 karakter hosszú sort lehet bevinni. A szövegkonstansokat idézőjelek közé kell zárni, de a záró idézőjel elhagyható. Két egymást követő zárójel ("") üres stringet jelöl, ez nem egyenlő a CHR(0)-val.
Szövegkonstans típusú változók - és string műveletek - használatára csak a 8K verzióban van lehetőség, az ilyen típusú változókban maximum 25 karakter hosszú szövegfüzéreket tárolhatunk.
Operátorok
Operátoroknak nevezzük a különféle műveleti jeleket, amelyek összekapcsolják a kifejezésben szereplő operandusokat. Az operandusok alatt változókat, konstansokat, függvényértéket értünk, de bármelyik operandus lehet egy újabb kifejezés.
- negálás (Pl.: a=-a) ^ hatványozás (csak a 8K-s változatban) *, / szorzás, osztás +, - összeadás, kivonás
= egyenlő <> nem egyenlő < kisebb > nagyobb <= kisebb vagy egyenlő >= nagyobb vagy egyenlő Egyenrangú műveletek esetén a kiértékelés balról jobbra haladva történik meg. A kiértékelés sorrendjét természetesen a zárójelek használatával megváltoztathatjuk.
NOT tagadás AND logikai / bináris és OR logikai / bináris vagy
A logikai igaz értéke -1, a hamis értéke 0.
Valós kifejezéseken bináris műveletet hajtanak végre. Pl:
63 AND 16 = 16
4 OR 2 =6
Szintaktikai szabályok
A BASIC program programsorokból áll, minden sor sorszámozott. Egy sorban több utasítás is állhat, kettősponttal elválasztva. A programsor maximális hossza 71 karakter. Az egyes nyelvi elemek között tetszőleges számú szóköz karakter állhat, mint elválasztó karakter, de ez akár teljesen el is hagyható (ez a program olvashatóságát persze nagymértékben rontja). Az alábbi három program lefuttatása egymással egyenértékű eredményt ad:
10 A$="Altair 8800"
20 FOR I=1 TO LEN(A$)
30 PRINT MID$(A$,I)
40 NEXT I10 A$="Altair 8800": FOR I=1 TO LEN(A$): PRINT MID$(A$,I): NEXT I
10A$="Altair 8800":FORI=1TOLEN(A$):PRINTMID$(A$,I):NEXTI
A változókat - beleértve a maximum 11 elemű tömböket - az első használat előtt nem szükséges deklarálni, ebben az esetben a valós változók kezdőértéke 0, a string-változóké üres szövegfüzér.
Parancsok és utasítások
CLEAR | |
Törli a változókat. A tárban lévő program sértetlen marad. A 8k-s verzióban még egy funkciója van az utasításnak: a stringek tárolására fenntartott (alapértelmezés szerint 50 byte) helyet állíthatjuk be, az alábbi formában használva: <CLEAR aritmetikai kif.> A CLEAR 200 utasítás hatására a szövegfüzérek tárolására fenntartott hely 200 byte lesz, a BASIC program tárolására ennyivel kevesebb hely marad, amiről a FRE függvénnyel meg is győződhetünk. (A sting-kifejezések eredményeiként előálló szövegfüzérek a BASIC munkaterület végén tárolódnak.) Parancs üzemmódban is használható. |
|
CLOAD | |
(Csak a 8k-s változatban) Eredetileg a megadott nevű programot betölti kazettáról. Az Enterprise változatban hatástalan. |
|
CONT | |
(Csak a 8k-s változatban) A STOP, vagy END utasítással, vagy a CTRL+C, STOP billentyűkkel megszakított program végrehajtását folytatja a programmegszakítás helyétől. A STOP utasítás felhasználásával ellenőrzőpontok iktathatók be a programba, majd megállítás - és pl. a változók értékeinek ellenőrzése - után a CONT-tal folytatható. A CONT parancs nem hajtható végre, ha a programon változtattunk, vagy hibával állt le. Csak parancs módban használható. |
|
CSAVE | |
(Csak a 8k-s változatban) Eredetileg a tárban lévő programot a megadott néven kimenti kazettára. Az Enterprise változatban hatástalan. |
|
DATA | |
A DATA utasítás nagy mennyiségű adat (számokat, stringeket) tárolására alkalmas, melyeket a READ utasítás segítségével olvashatunk be változóba, abban a sorrendben, ahogy a DATA utasításban követik egymást. A konstanslista elemei egymástól vesszővel elválasztott konstansok. A szövegkonstansokat nem szükséges idézőjelek közé rakni, kivéve, ha tartalmaz vessző karaktert is. A DATA utasításokban tárolt adatok beolvasási sorrendje a RESTORE utasítással megváltoztatható. Csak program üzemmódban használható. |
|
DEF | |
(Csak a 8k-s változatban) Az utasítás segítségével aritmetikai függvényt definiálhatunk, melyre aztán az FN függvényhívás segítségével hivatkozhatunk. Minden a felhasználó által definiált függvénynek egyetlen paramétere lehet, de a program változóinak értékét felhasználhatjuk a kifejezésben. Alakja: DEF FN<azonosító>(paraméter)=<aritmetikai kif.> Az azonosító (a függvény neve) maximum 5 karakterből állhat, de csak az első két karakter szignifikáns. Az FN foglalt szó és az azonosító között nem állhat szóköz. A paraméter valós típusú változó. A függvényt definiáló aritmeti9kai kifejezés legfeljebb egy sornyi lehet. Csak program módban használható. Pl: DEF FNSEC(X)=1/COS(X) DEF FNSCS(X)=1/SIN(X) |
|
DIM | |
A DIM utasítást követően megadott nevű, típusú tömbváltozót deklarálja a zárójelben megadott felső indexhatárokkal. 14755 Az alsó indexhatár minden esetben 0, a megadható felső indexhatár elvileg 14755, de ez a 8K verzióban is OM (elfogyott a memória) hibakódot eredményez. Egymás után több tömbváltozót is létrehozhatunk egy DIM utasítással. A 4K-s verzióban csak egydimenziós tömb definiálására van lehetőség, a 8K-s verzióban a dimenziók száma nincs korlátozva, a memória mérete miatt azonban maximum 7 dimenziós tömböt hozhatunk létre, de ez is csak elméleti lehetőség.) Parancs üzemmódban is használható. Pl: DIM A(3),B(10) DIM C$(5,6) DIM A(N,N*2) |
|
END | |
Az END végrehajtása a program futásának azonnali befejezését jelenti, ha a program tartalmaz magasabb sorszámú sort, az nem hajtódik végre. A CONT parancs a program futtásának folytatását eredményezi. Az interpreter parancs üzemmódban is végrehajtja, bár ennek nyilvánvalóan nincs értelme. |
|
FOR | |
Ciklusszervező utasítás, növekményes ciklusnak is nevezik, mert a ciklusmag egy ciklusváltozó egymás utáni értékeire hajtódik végre egy kezdőértéktől egy végértékig. A FOR ciklus szerkezete:
A FOR utasítás a FOR kulcsszóból, az azt követő ciklusváltozó azonosítójából, az értékadás-szimbólumból ( = ), a ciklusváltozó kezdeti értékét meghatározó kifejezésből, a TO kulcsszóból, a ciklusváltozó végértékét meghatározó kifejezésből, valamint a STEP kulcsszóból és a lépésközt meghatározó kifejezésből áll. Ha a kívánt lépésköz egy, a STEP és az azt követő kifejezés el is maradhat:
A lépésköz negatív is lehet, ebben az esetben a kifejezés2 értékének kisebbnek kell lennie, mint a kifejezés1 értéke. Ha a kifejezés1 (a ciklusváltozó kezdeti értéke) nagyobb mint a kifejezés2, és nincs STEP, vagy van de a kifejezés3 értéke pozitív, a ciklusmag akkor is lefut egyszer a ciklusváltozó kezdeté értékével. 10 FOR I=1 TO 10 |
|
GOSUB | |
Alakja: GOSUB <sorszám> Végrehajtja a GOSUB után megadott sorszámú programsorban kezdődő alprogramot. Az alprogram végét a RETURN kulcsszó jelzi. Ez azt jelenti, hogy feltétel nélküli vezérlésátadás jön létre a GOSUB utasításban megadott számú sorra. Amikor ezt követően a legközelebbi RETURN utasításhoz ér a program, a vezérlés visszakerül a GOSUB utasítást követő utasításra. A GOSUB utasítások egymásba ágyazhatóak. Ennek azonban határt szab - nem csak a program áttekinthetősége -, hanem a verem nagysága is. Parancs módban is használható. |
|
GOTO | |
Alakja: GOTO <sorszám> Feltétel nélküli vezérlésátadás. A program a GOTO utasításban megadott számú sor végrehajtásával folytatódik. Parancs üzemmódban is használható. |
|
IF | |
Feltételes vezérlésátadást hoz létre, attól függően, hogy az IF kulcsszót követő feltétel teljesül-e, vagy sem. Ha igen, akkor a THEN kulcsszót követő utasítás / utasítások kerülnek végrehajtásra, ha nem, akkor a következő programsorra kerül a vezérlés.
Alakja: IF <logikai kif.> THEN <utasítás> Mivel az igaz ág utasításait csak a THEN kulcsszó után lehet írni, egyetlen programsorba, nagyon gyakori az IF feltétel THEN GOTO <sorszám> szerkezet. Az interpreter megengedi, hogy ilyen esetben a GOTO kulcsszót elhagyjuk: IF <logikai kif.> THEN <sorszám> Az IF szerkezetet parancs módban is használhatjuk. |
|
INPUT | |
Az utasítás lehetővé teszi, hogy a billentyűzetről közvetlenül adatokat adjunk át egy futó BASIC programnak. Alakja:
INPUT <változólista> A változólista egy, vagy több (egyszerű-, vagy tömb-) változót tartalmaz, vesszővel elválasztva. Az utasítás végrehajtásakor egy kérdőjel jelenik meg a kurzor aktuális pozíciójában és a program adatbevitelre vár az ENTER megnyomásáig. Ha több változót vár az INPUT, azokat vesszővel elválasztva adhatjuk meg, vagy egyenként, minden érték bevitelét ENTER-rel lezárva. Mivel a megjelenő kérdőjel nem segíti a program felhasználóját, hogy megértse mit vár tőle a program, gyakori megoldás a PRINT és az INPUT egymás utáni használata. Pl.: PRINT "Hany eves vagy";:INPUT E Az előbbi példában szereplő PRINT utasítás "megspórolására" a 8k-s verzióba az INPUT utasítást az alábbi formában is használhatjuk: A 8k-s változatban hibát okoz, hogy ha számot vár az INPUT és szövegfüzért adunk meg. A 4k-s változatban mindenképen számot vár az utasítás, ezért a beolvasást az első betűig végzi. Pl. ha csak betűket adunk meg, a beolvasott érték nulla lesz. |
|
LET | |
Értékadó utasítás. Alakja: LET <valós változó>=<aritmetikai kif.> LET <string változó>=<string kif.> A LET kulcsszó kiírása nem kötelező. Ha egy utasítás első karaktere nem token, akkor az interpreter LET-et tételez fel. A megadott változó az egyenlőségjel jobb oldalán álló kifejezés értékét veszi fel. A változók egyszerű és tömbváltozók is lehetnek. A változók értékei akárhányszor, a program bármely részén megváltoztathatók. Az Altair BASIC nem ismeri a lokális- és globális változók fogalmát. Ez különösen az alprogramok megtervezésekor okozhat problémát. Ha egy rutint a program több részéről is meghívunk, akkor változóit más célokra nem célszerű használni. Parancs üzemmódban is használható. |
|
LIST | |
Alakja: LIST LIST <sorszám> A tárban lévő programot listázza ki a megadott sorszámú sortól, vagy a program elejétől kezdve. Program üzemmódban is használható. |
|
NEW | |
Törli a memóriában tárolt programot és a változókat. Az utasítás valójában nem törli a memória tartalmát, csupán a BASIC munkaterülethez kapcsolódó mutatókat állítja kezdőértékükre. Az interpreter ezután úgy tekinti, hogy üres a tár. Parancs és program üzemmódban is használható. |
|
NEXT | |
A FOR ciklus végét jelző utasítás. Alakja: NEXT <ciklusváltozó> (a 8k-s verzióban a NEXT után a ciklusváltozó már elhagyható.) Az utasítás hatására a vezérlés közvetlenül a NEXT-nek megfelelő FOR-t követő első utasításra kerül, feltéve, hogy a STEP-ben specifikált értékkel - ennek hiányában eggyel - megnövelt ciklusváltozó még mindig a megengedett tartományba esik. Ha nem, a NEXT-et követő első utasítás hajtódik végre. Lásd még a FOR utasítást. |
|
ON | |
(Csak a 8k-s változatban) Többirányú elágazást tesz lehetővé a GOTO vagy GOSUB utasításokkal együtt használva. Formája: ON <aritmetikai kif.> GOSUB <sorszámlista> vagy ON <aritmetikai kif.> GOTO <sorszámlista> A sorszámlista egymástól vesszővel elválasztott előjel nélküli egész konstansokat tartalmaz. Az aritmetikai kifejezést értékeli ki először az interpreter (az értékének 0-255 intervallumba kell esnie), majd a sorszámlista annyiadik elemének megfelelő programsorra adódik át a program vezérlése. Ha a kifejezés értéke 0, a programvégrehajtás az ON ... GOTO / ON ... GOSUB utasítást követő soron folytatódik. GOSUB esetén a verembe még a visszatérést biztosító információk is bekerülnek. Példa: ON (INT(RND(1)*5))+1 GOTO 100,200,300,400,500 |
|
OUT | |
Csak a 8k-s verzióban. Alakja: OUT I,J Az I számú portra adatot (J) ír ki. Az I, J aritmetikai kifejezés, értéküknek a 0-255 intervallumba kell esnie. |
|
POKE | |
Csak a 8k-s verzióban. Az utasítás segítségével egy tetszőleges RAM címre közvetlenül beírhatunk egy byte értéket. Alakja: POKE aritm.kif1,aritm.kif2 Az aritm.kif1 a memóriacímet jelöli, értékének 0-65535 közé kell esnie. Az aritm.kif2 a beírandó érték, értékének 0-255 közé kell esnie. Parancs- és program üzemmódban is használható. |
|
Aritmetikai kifejezéseket, változók értékeit, szövegfüzéreket nyomtat az elsődleges kimenetre, általában a képernyőre. A szövegfüzéreket idézőjelek között kell megadni. A nyomtatási kép kialakítására használhatjuk a következő szeparátorokat: vessző (,), pontosvessző (;), SPC, TAB függvények. Ha a kiírandó elemeket pontosvesszővel választjuk el egymástól, a nyomtatás a következő karakterhelytől folytatódik, ha vesszővel -, a következő tabulátor pozícióban. Ha a PRINT utasítást nem zárja szeparátor, automatikusan CR/LF karakterpár is kiírásra kerül (azaz a következő PRINT új sorban folytatja a kiírást. A 8k-s verzióban nem csak megjeleníthető karaktereket tartalmazó szövegfüzéreket írhatunk ki, hanem vezérlő karaktereket is (a CHR$ függvény segítségével). A 26-os ASCII kód kiírásával (PRINT CHR$(26)) képernyőtörlést hajthatunk végre. A 8K-s változatban a PRINT kulcsszó helyettesíthető a kérdőjellel (?). Pl: PRINT "2+3=";2+3 PRINT A,B,C ?"Altair 8800" |
|
READ | |
A DATA utasításokban definiált értékeket olvassa be sorban és rendeli hozzá az utasításban megadott változókhoz. Alakja: READ <változólista> A változólista tetszőleges típusú, egymástól vesszővel elválasztott egyszerű- vagy tömbváltozókat tartalmaz. Legalább egy változó megadása kötelező. Hibát eredményez, ha a változó és a DATA utasításban talált érték típusa nem felel meg egymásnak, vagy ha a DATA utasításokban tárolt adatok elfogytak. (Ezen segíthet a RESTORE utasítás). |
|
REM | |
Lehetővé teszi megjegyzések (tetszőleges karaktersorozat) beírását a program szövegébe. Az interpreter a REM észlelésétől a sor maradék részét már nem hajtja végre, hanem a következő sor elejétől folytatja a program végrehajtását. | |
RESTORE | |
Az utasítás hatására a READ újra az első DATA sorból olvassa a következő értéket. | |
RETURN | |
Az utasítás hatására a program vezérlése az utolsó GOSUB utasítást követő első utasításra kerül. | |
RUN | |
Alakja: RUN RUN <sorszám> A memóriában tárolt programot az elejétől (a legalacsonyabb sorszámú sortól), vagy a megadott sorszámú sortól futtatja. Törli a változókat, és legelső DATA sor lesz aktuális. Program üzemmódban is használható. |
|
STEP | |
Lásd FOR. | |
STOP | |
Megállítja a program futását, a 8k-s verzió kiírja, hányadik sorban állt meg a program. A program futtatása a CONT utasítással folytatható. Az utasítást elsősorban programfejlesztés során használjuk, segítségével töréspontokat helyezhetünk el a programban. A program megszakítása után a PRINT segítségével ellenőrizhetjük a program változóinak értékét. |
|
THEN | |
Lásd IF. | |
TO | |
Lásd FOR. | |
WAIT | |
Csak a 8k-s verzióban. Alakja: WAIT I,M1,M2 vagy WAIT I,M1 Ahol 0 <= I, M1, M2 <= 255. Az utasítás felfüggeszti a program végrehajtását, amíg a paramétereiben specifikált esemény be nem következik. Az I kifejezés egy port címét jelenti. Az utasítás először kiszámítja az (INP(I) EOR M2) AND M1 értékét (EOR) a kizáró VAGY). Ha az eredmény nullától különböző a program végrehajtása a következő sortól folytatódik. Ha az eredmény nulla, az interpreter a fenti műveletet - akár a végtelenségig - ismétli. I-nek tehát olyan címnek kell lennie, amit megszakító rutin vagy a perifériák használnak. Ha M2-t nem adtuk meg, akkor az értéke nulla, tehát csak a INP(I) AND M1 hajtódik végre. Az az esemény, amelyik a BASIC program futásának folytatását eredményezi az I port értékének valamely bitjének magasba és/ vagy alacsonyra állítódása lehet. Az M1-ben magasra kell állítani azokat a biteket, amelyek értékére kíváncsiak vagyunk, a többit pedig alacsonyra. M2-ben azokat a biteket kell magasra állítani, amelyek értékének alacsonyra kell váltania a futás folytatásához. Ha például M1 = 00011000 = 24 és M2 = 00010000 = 16, akkor a program addig áll, amíg I port 4 bitje alacsony és 5. bitje magas nem lesz. |
Függvények
Az Altair BASIC-ben valamennyi függvénynek (a MID$ függvény kivételével) egy vagy két argumentuma van, akkor is, ha az csak formális paraméter. Ezért a függvények alakja minden esetben a következő:
függvénynév(argumentum1)
vagy
függvénynév(argumentum1,argumentum2)
ABS | |
Az ABS függvényt zárójelben követő aritmetikai kifejezés abszolút értékét adja. Az ABS mindig egy nem negatív értékkel tér vissza: ABS(3) = 3 ABS(0) = 0 ABS(-2) = 2 |
|
ASC | |
(Csak a 8k-s változatban) A paraméterként megadott szövegfüzér első karakterének ASCII kódját adja: ASC("ABC") = 65 |
|
ATN | |
Csak a 8k-s verzióban. A radiánban megadott szög árkusz tangensének főértékét adja. |
|
CHR$ | |
Csak a 8k-s verzióban. A megadott ASCII kódszámú karaktert adja vissza. A paraméternek a 0-255 intervallumba kell esnie. |
|
COS | |
(Csak a 8k-s változatban) A radiánban megadott szög koszinuszát számítja ki. |
|
EXP | |
(Csak a 8k-s változatban) Exponenciális függvény, e^x kiszámítására szolgál, ahol e egy matematikai állandó, a természetes alapú logaritmus alapja, értéke körülbelül 2.718281828 |
|
FN | |
Csak a 8k-s verzióban. A DEF utasítással definiált függvényt hívja meg. Alakja: FN<azonosító>(paraméter) Példa: PRINT FNSEC(3) LET A=FNCSC(3) |
|
FRE | |
Csak a 8k-s verzióban. Ha a függvény paramétere numerikus kifejezés (pl. FRE(0)), megadja byte-ban, a BASIC munkaterület számára meglévő szabad memóriaterületet. Ha a függvény paramétere tetszőleges string típusú kifejezés (pl. FRE("")), megadja byte-ban a szövegfüzérek tárolására rendelkezésre álló szabad memóriaterületet. Ez kezdetben 50 byte, melyet a CLERAR utasítással módosíthatunk. |
|
INP | |
Csak a 8k-s verzióban. A megadott számú portról olvas be adatot. A kifejezés értékének a 0-255 intervallumba kell esnie. |
|
INT | |
Az argumentum egész részét adja. : INT(3.6) = 3 Ha egy számot valóban kerekíteni akarunk, akkor 0.5-öt hozzá kell adni, és utána venni az egész részét: INT(X+.5) |
|
LEFT$ | |
Csak a 8k-s verzióban. A string függvény egy adott szövegfüzér megadott számú első karakteréből egy új string-et képez. Formája: LEFT$(<szövegfüzér>,<aritmetikai kif.>) Pl.: LEFT$("Kovacs Peter",6) = "Kovacs" |
|
LEN | |
Csak a 8k-s verzióban. A paraméterként megadott string-kifejezés karakterhosszát adja meg. |
|
LOG | |
Csak a 8k-s verzióban. Aritmetikai függvény, amely argumentumának e alapú logaritmusát számolja ki, Az EXP függvény inverze. A függvény segítségével tetszőleges Y alapú logaritmusát is kiszámolhatjuk X-nek: LOGy(X)=LOG(X)/LOG(Y) |
|
MID$ | |
Csak a 8k-s verzióban.
2 vagy 3 paraméteres string függvény, mely az első paraméterként megadott szövegfüzér bizonyos egymás után következő karaktereiből egy új stringet állít elő.
A LEFT$ és a RIGHT$ függvények a MID$ segítségével kifejezhetők: |
|
NULL | |
PEEK | |
Csak a 8k-s verzióban. Az argumentumként megadott sorszámú memóriacímen lévő byte értékét adja. A kifejezés értékének a 0-65535 intervallumba kell esnie. |
|
POS | |
Csak a 8k-s verzióban. Megadja, hogy a kurzor hány karaktert mozdult el az aktuális képernyő sorban (vagyis a kurzor pillanatnyi pozíciója a visszaadott értéknél eggyel nagyobb). A függvénynek formális paramétere van, értéke lényegtelen. Általában POS(0) alakban használatos. |
|
RIGHT$ | |
Csak a 8k-s verzióban. A string függvény egy adott szövegfüzér megadott számú utolsó karakteréből egy új string-et képez. Formája: RIGHT$(<szövegfüzér>,<aritmetikai kif.>) Pl.: RIGHT$("Kovacs Peter",5) = "Peter" |
|
RND | |
Forma: RND(aritmetikai kifejezés) 0-1 zárt intervallumba eső pszeudo-véletlen számokat generál. Az RND utasítás természetesen nem állít elő "igazi" véletlen számokat. Az argumentum előjele határozza meg, milyen eljárás segítségével számítja ki az interpreter a következő számot:
|
|
SGN | |
A paraméterként megadott aritmetikai kifejezés előjelét adja vissza (ha a kifejezés negatív, a visszaadott érték: -1, ha pozitív: 1, ha a kifejezés értéke nulla, a visszaadott érték is nulla). |
|
SIN | |
A radiánban megadott szög szinuszt számítja ki. A 4K-s verzióban nincs koszinusz függvény, ezt a SIN függvény segítségével számolhatjuk ki: COS(x)=SIN(X+3.14159/2) |
|
SPC | |
Csak a 8k-s verzióban. A paraméterként megadott számú szóközt nyomtat a kurzor aktuális pozíciójától kezdve. A függvény csak a PRINT utasításban szerepelhet. Az SPC és a ( jel között nem lehet szóköz. A paraméter értékének - lefelé kerekítés után - a 0-255 intervallumba kell esnie. |
|
SQR | |
Az argumentum négyzetgyökét számolja ki. SQR(X)=X^0.5 |
|
STR$ | |
Csak a 8k-s verzióban. Az argumentumként megadott aritmetikai kifejezés értékének sting-alakját adja. Pl: STR$(123) = "123" STR$(-1000000) = "-1E+06" |
|
TAB | |
Amennyiben a kurzor pillanatnyi vízszintes pozíciója az adott sorban kevesebb, mint a TAB paramétereként megadott érték, addig a pozícióig szóközöket nyomtat. A függvény csak a PRINT utasításban szerepelhet. A TAB és a ( jel között nem lehet szóköz. |
|
TAN | |
Csak a 8k-s verzióban. A radiánban megadott argumentumának tangensét számítja ki. tg(x)=sin(x)/cos(x) |
|
USR | |
A paraméterként megadott memóriacímen kezdődő gépi kódú programot hajtja végre. A paraméter értékének a 0-65535 intervallumba kell esnie. |
|
VAL | |
Csak a 8k-s verzióban. A paraméterként megadott string-kifejezést számmá konvertálja. A konverziót az első nem szám karakterig végzi. Mivel az INPUT utasítás nem végez típusellenőrzést, hibát és a programfutás megszakadását okozza, ha a felhasználó szám helyett szövegfüzért ad meg a programnak (csak a 8ks- változatban). Az ilyen hibát lehet kivédeni azzal, ha az INPUT utasítással szövegfüzért olvasunk be, majd ezt alakítjuk számmá a VAL függvénnyel. Pl.: VAL("123.321") = 123.321 |
Hibakódok
4K és 8K verzióban:
BS | Bad Subscript. Tartományon kívüli tömbindex. Pl. DIM A(20) utasítás után LET A(21)=... |
DD | Double Dimension. Duplán deklarált tömbazonosító. Már létező tömb nevével kíséreltünk meg újabb tömböt létrehozni. |
FC | Function Call error. A meghívott függvénynek hibás paramétert kíséreltünk meg átadni, vagy a tömbhivatkozás indexe negatív szám. Akkor fordulhat elő: - ha a LOG függvényt nulla, vagy negatív értékkel, az SQR függvényt negatív értékkel hívjuk meg, - a MID$, LEFT$, RIGHT$, INP, OUT, WAIT, PEEK, POKE, TAB, SPC függvényekben, vagy az ON ... GOTO utasításban rossz paramétert adunk meg. |
ID | Illegal Direct. A DEFFN függvénydefiníciót, vagy 8K-s verzióban az INPUT utasítást parancsmódban akartuk használni. |
NF | NEXT without FOR. A NEXT utasításhoz nem tartozik FOR ciklusszervező utasítás. |
OD | Out of Data. A DATA sorokban definiált adatlista végére ért a program, és újabb READ utasítással próbált belőle adatot olvasni. A DATA sorokban több adatot kell megadni, vagy a RESTORE utasítást kell használni. |
OM | Out of Memory. Elfogyott a memória. A program túl nagy, túl sok változót használ, vagy túl sok FOR ciklusszervező utasítás, GOSUB szubrutinhívás van egymásba ágyazva. |
OV | Overflow. Szám túlcsordulás. Az aritmetikai kifejezés értéke túl nagy ahhoz, hogy a BASIC számformátumában ábrázolni lehessen. Ha alulcsordulás történik (azaz a kifejezés értéke kisebb, mint a legkisebb ábrázolható szám), akkor a művelet eredménye nulla, és a végrehajtás hibajelzés nélkül folytatódik! |
SN | Syntax Error. Szintaktikai hiba. Pl. Hiányzik egy zárójel, érvénytelen karakter szerepel az utasításban. |
RG | RETURN without GOSUB. A RETURN utasításhoz nem tartozik GOSUB. Pl. a főprogram nincs megfelelően elkülönítve a szubrutinoktól, és a végrehajtás valamelyik szubrutinra fut. |
US | Undefined Statement. A GOTO, GOSUB, THEN utasításokban hivatkozott sorszámú programsor nem létezik. |
/0 | Division by Zero. Nullával való osztás. |
Csak a 8K verzióban:
CN | Continue error. A program folytatása nem lehetséges (a CONT utasítással). Vagy azért, mert a program futása hiba miatt szakadt meg, vagy a program megszakítása után módosítottuk a programot. |
LS | Long String. Kísérlet történt az összefűzési operátor használatával 255 karakternél hosszabb karakterlánc létrehozására. |
OS | Out of String Space. A karakterláncok tárolására fenntartott memóriaterület betelt. |
ST | String Temporaries. Egy karakterlánc típusú kifejezés túl összetett. Kettő vagy több rövidebbre kell felosztani. |
TM | Type Mismatch. Típus eltérés. Pl. egy numerikus változóban szövegfüzér típusú kifejezést akarunk tárolni (LET), vagy a meghívott függvénynek adtunk meg rossz típusú kifejezést paraméternek. |
UF | Undefined Function. Hibás függvényhívás. Nem létező (nem definiált) függvényt kíséreltünk meghívni. |