Modă și stil

Limba paradisului. Un limbaj adaptabil în curs de dezvoltare pentru sistemul de programare interactiv DSSP. Traduceri sacru și profan

Limba paradisului.  Un limbaj adaptabil în curs de dezvoltare pentru sistemul de programare interactiv DSSP.  Traduceri sacru și profan

1. Aceasta este o poveste despre cum oamenii au încetat să se mai înțeleagă și au apărut numeroase limbi lumea modernă. Cât de popular este acest mit între diferite națiuni și care sunt interpretările lui?

2. Mitul Turnului Babel se bazează nu numai pe credința că inițial toată omenirea vorbea aceeași limbă, ci și pe faptul că această limbă era „ideală”: numele obiectelor le transmiteau adevărată esență. Reprezentanții altor culturi împărtășesc aceste puncte de vedere și cred ei că limba lor este cea mai apropiată de originală?

Răspunsul la prima întrebare este oferit în Cartea Vechiului Testament din Geneza 11:1-9, care spune că Dumnezeu a decis să pedepsească rasa umană punând asupra ei blestemul confuziei limbilor. Răspunsul la a doua întrebare poate fi găsit în Geneza 2:19. În această parte, Dumnezeu a adus la Adam toate animalele și păsările pentru a auzi cum le va numi Adam și „orice numește un om fiecărui suflet viu, acesta este numele lui”. Un tur improvizat al diferitelor culturi ne va permite să vedem cum sunt acoperite aceste probleme. În ceea ce privește prima dintre ele, mulți sunt de acord cu Vechiul Testament: diversitatea limbilor este o pedeapsă a Domnului sau, cel puțin, o consecință a vreunui factor nefavorabil.

Legenda unuia dintre triburile australiene povestește despre mâncarea bătrânilor. Triburile care au mâncat trupul vorbeau un limbaj „pur”, iar cei care au mâncat organe interne, - pe „necurat”. Kabilei africani cred că oamenii au început să vorbească diferite limbi ca urmare a conflictului. Potrivit unui trib din Assam, confuzia limbilor s-a datorat faptului că trei copii au vânat odată un șobolan. Unul dintre triburile amazoniene este de părere că Dumnezeu a separat oamenii și limbile lor, astfel încât să devină mai ascultători de El. Dintre populația indigenă a Americii, tribul Maidu (California), se crede că inițial oamenii vorbeau aceeași limbă, dar într-o zi, la o ceremonie de înmormântare, limba a încetat să mai fie uniformă. Irochezii cred că separarea limbilor s-a datorat unei certuri de familie în care un copil a fost ucis. Dar presupunerea că limbile multilingve sunt un blestem nu este atât de răspândită pe cât pare. Există multe versiuni în lume conform cărora diviziunea a avut loc ca urmare a proceselor naturale.

Vechiul imn sacru indian „Rig Veda” menționează că odată a existat Vak („cuvânt”) și zeii l-au împărțit în multe forme. Popoarele din Peninsula Indochina povestesc despre șase rase, fiecare dintre ele având propria sa limbă sub forma unei tulpini care ieșeau dintr-o tărtăcuță. Tribul Quiché (Guatemala) are un mit conform căruia oamenii trăiau împreună și vorbeau aceeași limbă până când s-au împărțit în grupuri. Fiecare și-a ales un zeu și a început să-și vorbească propria limbă.

Mitul creației navajo din America de Sud povestește despre „Femeia în schimbare” și despre apariția unor popoare reale care vorbeau limba ei. Așadar, ea a creat popoare vecine - Pueblos, aborigeni mexicani și altele, și își vorbeau propriile limbi, răspândindu-le în direcții diferite. În Islam, Coranul învață că Adam nu a inventat nume sau orice altceva, ci a fost învățat totul de Allah. Diversitatea limbilor este absolut naturală și este o manifestare a puterii lui Allah. Toți oamenii sunt capabili să înțeleagă revelațiile Coranului, indiferent în ce limbă sunt scrise.

Sistemul mitologic al multor popoare ale lumii nu are nicio explicație pentru confuzia limbilor, care este pur și simplu luată de la sine înțeles și, prin urmare, nu poate răspunde la întrebarea noastră. Cu toate acestea, în aproape toate culturile lumii există o mențiune despre o limbă „ideală” (întrebarea 2). Mai sus am menționat un trib australian care crede că unii oameni (care se hrănesc cu corpul uman) vorbesc un limbaj „pur” care transmite adevărata esență a lucrurilor. Potrivit vechilor egipteni, zeul Ptah a dat nume tuturor, astfel limbajul a devenit un dar de la zei. În China, limba „corectă” a fost predată de împărați mitici. Coranul vede diversitatea limbilor ca diviziuni ale unei singure limbi care le include pe toate celelalte.

Pretutindeni oamenii încearcă să înțeleagă cum numele unui obiect își dezvăluie esența. Se presupune că fie un limbaj „ideal” care descrie adevărata esență a unui subiect există astăzi, fie este un lucru din trecut. A doua presupunere servește ca o condiție prealabilă pentru căutarea adevărului și armoniei în lume. Se pare că ideile despre legătura limbajului cu lumea reală și cu existența umană sunt încorporate în conștiința noastră. În acest sens, apare o întrebare, exprimată pentru prima dată în dialogul lui Platon „Cratylus” și care de atunci a făcut obiectul unei dezbateri constante: este legătura dintre nume și esența obiectivă a lucrurilor naturale (care apar în conștiința subiectivă a vorbitorului nativ). ) sau această legătură este condiționată și accidentală?

Limba este un sistem de semne care vă permite să treceți de la semnificația și sensul unui concept la desemnarea acestuia.

Omul este o ființă verbală și, spre deosebire de animale, comunică cu propriul soi folosind limbajul. Uneori vorbesc despre „limbajul animalelor”, dar este clar că o astfel de expresie este condiționată - în bogăția și capacitățile sale, limbajul animalelor nu este similar cu cel uman. Îngerii nu au nevoie deloc de limbă pentru comunicarea lor - este dificil să-i imaginezi vorbind rusă sau engleză.

Funcțiile limbajului pot fi diferite - pe lângă transmiterea de informații, ajută la exprimarea sentimentelor și aprecierilor.

Poate fi tradusă Scriptura?

Limbajul Bisericii este limbajul rugăciunii, al închinării și al Scripturii.

În unele religii, textele sacre există inițial într-o singură limbă și sunt considerate fundamental intraductibile. Astfel, Coranul musulman a fost compilat inițial în arabă. Mai mult, musulmanii cred că așa a fost creată această carte la începutul timpurilor.

Cărturarii evrei erau, de asemenea, înclinați către ideea posibilității de a scrie texte sacre numai în ebraică. Acesta nu a fost cazul Scripturii creștine în primul rând.

În secolul al III-lea î.Hr. Așa-numita „traducere a celor șaptezeci” a fost finalizată - Septuaginta - o traducere a Vechiului Testament în greacă. Mai mult, unii cercetători cred că Septuaginta a fost cea care a jucat rolul Sfintei Scripturi în vremurile intertestamentale.

Existența Septuagintei a devenit principalul argument în favoarea traducebilității fundamentale a Scripturii. Există, totuși, una și mai puternică. Acum se consideră dovedit că Hristos a vorbit apostolilor în aramaică. Dar compilatorii Evangheliilor, fără îndoială, au transmis aceste conversații în greacă.

Acum există o direcție științifică - reconstrucții lingvistice. Compilatorii lor încearcă să înțeleagă cum au sunat aceste dialoguri în original. Dar acesta este încă un subiect de cercetare științifică.

Este cu adevărat în rai?Rece?

Când traduceți o limbă într-o limbă, uneori apar probleme deoarece limbile nu sunt identice din punct de vedere gramatical. Semnificațiile și nuanțele cuvintelor în diferite limbi sunt, de asemenea, diferite.

De exemplu, expresia „paradisul este un loc verde și răcoros” arată clar că Scriptura a fost creată în țări cu un climat cald, unde „răcorul” este destul de plăcut. În rusă, cu greu ar apărea astfel de asociații. Iar verbul „rece” în sensul „relaxează-te”, „distrează-te” a venit în rusă ca hârtie de calc din ebraică până în greacă.

Toți slavii au înțeles Biblia?

Scriptura nu a fost adusă strămoșilor noștri în limba rusă. Chiril și Metodiu - grecii din Salonic - au dezvoltat o nouă limbă scrisă bazată pe limba vorbita Slavii Solunsky.

Există multe popoare în lume care folosesc limbi care nu au o limbă scrisă. Atâta timp cât vorbim despre viața de zi cu zi, nu există probleme. Dar, de îndată ce un text religios sau un tratat filozofic trebuie tradus într-o astfel de limbă, limbajul trebuie îmbunătățit, ceea ce au făcut Chiril și Metodie.

Dacă presupunem că era mai ușor pentru triburile slave în urmă cu câteva mii de ani să cadă de acord între ele decât pentru popoarele slave moderne, atunci vom avea dreptate - limbile erau mai apropiate. Dar asta nu înseamnă că traducerea Scripturii făcută de Chiril și Metodie a fost mai de înțeles pentru oamenii din Kiev și Novgorod - scrisă limbaj literar mai era unul.

Poate că aceasta este o caracteristică a situației ruse, deoarece limba literară rusă este mai aproape de slavona bisericească decât de dialectul de la Moscova. De fapt, întreaga limbă slavonă bisericească a intrat în limba rusă ca un „calm ridicat”. De exemplu, chiar și participiile moderne - cum ar fi plânsul, alergarea - sunt formate exact după modelul slavonesc bisericesc - în rusă veche ar fi „plâns”, „alergare”.

Uneori, analogii ruși vechi au fost abandonați cu totul - „bun” și „bologoe” în numele „Bologoe”; „shelom”, care este doar în epopee, în contrast cu „cască”.

Limbile sunt apropiate și... paralele

ÎN Rusiei antice a existat o situaţie de diglosie. Acest lucru nu este același lucru cu „bilingvism”. Diglosia este utilizarea a două limbi în paralel în societate. De exemplu, în secolul al XIX-lea au fost folosite atât rusă, cât și franceză. Franceza era limba inalta societate, dar, în principiu, orice text putea fi tradus.

În diglosie, limbile nu se suprapun în sfera lor de utilizare. Vorbeau rusă veche și puteau scrie notițe de zi cu zi în rusă veche. Dar s-au rugat în slavonă bisericească.

Această situație a existat înainte de Petru în secolul al XVIII-lea, s-a prăbușit treptat. Acum știința și literatura s-ar putea dezvolta în limba rusă, dar doar rugăciunile mai există în slavona bisericească. Traduceți anunțul în slavona bisericească și va arăta ca o glumă sau o blasfemie.

Preot sau cioban?

Trăim într-o eră unică. ÎN Rusia țaristă Biblia putea fi citită în rusă, iar în Rus' antică putea fi ascultată în slavonă bisericească. Dar majoritatea oamenilor erau analfabeți sau nu erau suficient de educați pentru a citi și înțelege Scriptura.

ÎN ora sovietică Toți au devenit alfabetizați, dar nu a existat un text din Scriptură.

Acum alfabetizarea este încă păstrată și textele sunt accesibile.

Pe lângă Scriptura în sine, suntem invitați să stăpânim un anumit număr de texte slave - de la rugăciuni la închinare. Adevărat, traducerea existentă în rusă este oarecum greu de înțeles. În secolul al XIX-lea, neavând analogi, traducătorii au transferat adesea slavismul în traducere.

Așa a fost tradusă expresia „Eu sunt păstorul cel bun”. Și aici sunt câteva dificultăți. O traducere literală din greacă ar fi: „Sunt un păstor bun”, dar o astfel de traducere este percepută ca slabă. Pe de altă parte, acum simplul ascultător va percepe sublimul „păstor” mai degrabă ca „preot”. Cu toate acestea, trebuie să admitem că o traducere literală în limba rusă a multor vorbe biblice este imposibilă - expresia „prin buzele unui copil vorbește adevărul” nu va fi percepută ca o vorbă filozofică.

Dar, în general, percepția textului slav al Bibliei este împiedicată mai degrabă de lipsa de înțelegere a sensului, decât de cuvinte.

Dificultate separată - structuri gramaticale. De exemplu, există o serie de îmbunătățiri care provin din greacă. „Iertați păcatele și greșelile” înseamnă pur și simplu a ierta toate păcatele. Construcții precum „Am fost supărat de furie” și „Am iubit cu dragoste” sunt similare.

La traducerea textelor sacre în alte limbi, apar și probleme (deși popoarele în ale căror limbi Scripturile nu au fost încă traduse sunt, probabil, 5℅ din populația Pământului). Adică lucrarea pe care Chiril și Metodiu au făcut-o pentru slavi continuă.

Chiril și Metodiu nu au fost primii - înainte au existat traduceri în etiopică și gotică. După Chiril și Metodie, Ștefan din Perm a tradus Scripturile în limba Zyryan.

Traduceri sacru și profan

Fiecare traducere este considerată un text sacru? Nu, dar numai în măsura în care este acceptat în comunitățile bisericești. De exemplu, traducerea sinodală ca traducere liturgică nu este interzisă, dar nu este acceptată. Dar este folosit ca atare de protestanți, de exemplu, baptiștii ruși.

Există chiar și mișcări moderne ale protestantismului care cred că textul biblic ar trebui să fie accesibil tuturor. Sunt publicate și benzi desenate bazate pe povești biblice.

Nu există probleme cu textul Noului Testament - sursa lui este cunoscută în greacă. Dar baza traducerii sinodale Vechiul Testament textul a devenit ebraic. Fragmente din traducere greaca au fost inserate numai atunci când discrepanțele erau fundamentale.

ÎN versiunea modernă ar fi frumos să avem două traduceri – atât din textele masoretice ebraice, cât și din greacă. Acest lucru ar fi convenabil pentru cei care nu cunosc ambele limbi.

Răspunsuri la întrebări

După cuvântare, protopopului Alexandru i s-au adresat mai multe întrebări:

Ce limbă vorbea Adam?

- Greu de spus. Pe de o parte, limba se schimbă în timp ce este în viață. Dar nimeni nu știe dacă aceasta a fost o nouă proprietate a limbilor care a apărut după construirea Turnului Babel.

Dar, în orice caz, limba lui Adam era probabil diferită de orice altă limbă existentă, inclusiv ebraica.

Există în prezent o dezbatere despre traducerea serviciilor divine în rusă?

– Această idee a fost discutată chiar înainte de revoluție și a fost parțial compromisă de renovaționişti. Nu toți au servit în rusă, dar ideea a fost susținută de ei.

Traducerea Bibliei în rusă nu a fost ușoară, deși ideea mitropolitului Filaret că era necesar să se traducă atât din ebraică, cât și din greacă a fost o decizie înțeleaptă. Deși acest lucru nu ne-a oferit traduceri științifice din ambele limbi.

Există cazuri izolate de utilizare a limbii ruse - rugăciunea bătrânilor Optina și acatistul „Slavă lui Dumnezeu pentru toate” au fost scrise inițial în limba rusă.

Există atât de multe alte traduceri și vor fi atât de multe nuanțe atunci când le executați texte mai simple Rusifică oarecum mai degrabă decât traduce.

Acest proces se desfășoară spontan de mult timp. Uneori apar incidente: de exemplu, în „Ritul de nuntă” numărul dual este uneori înlocuit în mod neașteptat de plural, iar în acatistele moderne este folosit inconsecvent.

Cum participă cineva la educație? limbi diferite Providența divină?

– Limbajul există în afara voinței umane. O persoană poate crea Esperanto, dar limbile naturale există conform propriilor legi.

Chiril și Metodie au tradus în slavona bisericească prin inspirație de sus, dar și după modelul care exista la acea vreme.

Prin inspirație divină, scriind Evangheliile în limba greacă, apostolii au pus ideea de traducere a Evangheliei.

Pregătit de Daria Mendeleeva

Fotografie de Dmitry Kuzmin

Dezvoltarea limbajului adaptiv RAYA al sistemului de programare interactiv DSSP Moscova Universitate de stat Facultatea de Matematică Computațională și Cibernetică N.P. Brusentsov, V.B. Zakharov, S.A.

Descrierea generală a limbajului PARADIS

Scopul și scopul dezvoltării limbajului

RAYA (Evolving Adaptive Language) este limbajul de bază al Sistemului de Programare Structurată Dialogue DSSP. De bază - înseamnă că este baza pentru toate construcțiile ulterioare efectuate în DSSP prin dezvoltare (extindere, consolidare) limbajul de bazăși, poate, adaptarea mijloacelor lingvistice astfel create la o aplicație specifică. Spre deosebire de așa-numitele limbaje de nivel înalt, RAYA nu furnizează tipuri de date și operațiuni gata făcute, ci doar elemente și primitive pentru definiție eficientă tipurile necesare. De exemplu, formatele de date originale sunt octeți de 8 biți, cuvânt de 16 biți și cuvânt lung de 32 de biți, interpretate în funcție de operațiunile efectuate asupra acestora ca numere întregi, vectori booleeni, coduri de caractere, booleeni, indicatori de date și proceduri. În acest caz, este posibil, pe de o parte, să se manipuleze biți individuali de octeți și cuvinte și, pe de altă parte, să se formeze unități de date compozite (cuvinte de lungimi multiple, vectori, matrice, linii de text etc.) , stabilindu-le pentru acestea una sau alta interpretare introducerea unor operatii adecvate. Astfel, pot fi introduse numere reale cu lungimea și intervalul de valori necesare, numere complexe și alte obiecte și o versiune a limbajului concentrată pe aceasta aplicație, va include obiecte și mijloace caracteristice acestei aplicații și nu va include ceea ce nu se aplică acesteia - limbajul va fi adaptat (adaptat) aplicației. Dezvoltarea DSSP a avut ca scop crearea unui sistem accesibil pe scară largă și remediu eficient programarea microcalculatoarelor, de ex. calculatoare construite pe microprocesoare. O caracteristică esențială a arhitecturii microprocesorului este natura elementară a tipurilor de date și a operațiunilor, ceea ce înseamnă, pe de o parte, universalitate și, pe de altă parte, o programare care necesită multă muncă. Datorită versatilității lor, microprocesoarele și microcalculatoarele create pe baza lor au potențialul posibilități nelimitate aplicatii. Cu toate acestea, implementarea practică a acestor capabilități este limitată în primul rând de complexitatea dezvoltării programelor de aplicație necesare. Mai mult decât atât, programele de aplicație satisfăcătoare pot fi create doar cu o cunoaștere profundă și subtilă a specificului aplicațiilor relevante, i.e. Acestea ar trebui să fie dezvoltate nu doar de programatori, ci și de specialiști cu înaltă calificare într-un anumit domeniu. Prin urmare, sistemul de programare nu numai că ar trebui să mărească foarte mult productivitatea muncii programatorilor, ci și să fie atât de simplu încât să poată fi stăpânit și utilizat eficient de programatori neprofesioniști.

O soluție radicală la această problemă ar părea a fi o simplificare semnificativă a arhitecturii computerelor. Dar, din păcate, arhitectura microcalculatoarelor se dezvoltă în direcția diametral opusă - pe calea creșterii complexității și rafinamentului, astfel încât pentru un programator profesionist nu este ușor să stăpânească perfect limbajul de asamblare al microcalculatoarelor astăzi. Limbajele de programare de sistem, cum ar fi C sau PL/M, au redus intensitatea muncii pentru dezvoltarea programului într-o anumită măsură (deși departe de a fi suficientă), dar cu greu pot fi recomandate persoanelor care nu au experiență în programare. Un limbaj accesibil pe scară largă ar trebui, desigur, să fie mai simplu și mai natural și ar trebui să se bazeze, pe cât posibil, pe idei cotidiene, familiare, despre esența și tehnica programării.

Pe lângă accesibilitate și o reducere semnificativă a intensității muncii a dezvoltării programului în comparație cu programarea în limbaj de asamblare, DSSP trebuia să aibă universalitate a limbajului, la fel ca cea a limbajului de asamblare, eficiență ridicată a mașinii (adică compactitatea și viteza codului). ), fiabilitatea verificării programelor create și mentenabilitatea și modificabilitatea acestora, precum și mobilitatea (portabilitatea) sistemului și a programelor dezvoltate în acesta la mașini cu arhitecturi diferite.

Programare procedurală

Programarea în limbajul PARADISE este destul de asemănătoare cu tipuri atât de răspândite de activitate umană, cum ar fi planificarea și organizarea acțiunilor, lucrărilor, proceselor interconectate sau proiectarea obiectelor materiale complexe - mașini, unități, structuri. Asemenea unui designer care își realizează ideea prin agregarea părților sale componente (blocuri, ansambluri, piese), programatorul sintetizează acțiunea complexă necesară din cele oferite de limbaj. actiuni simple. De asemenea, putem spune că programarea (proiectarea) constă în descompunerea (descompunerea) treptată a obiectului fiind implementată în componente din ce în ce mai mici.

În limbajul PARADIS, principalul „construct” este o procedură - o acțiune numită. Limbajul se bazează pe un set limitat de proceduri simple (primitive), reprezentate prin nume proprii (notații). De exemplu: + înseamnă „adăugați”, NEG înseamnă „schimbați semnul”, VCTR înseamnă „creați vector”. În special, există primitive: și; (virgulă și punct și virgulă) permițându-vă să introduceți o nouă procedură, de exemplu, cu numele P, definindu-l ca o secvență de proceduri P1, P2, ..., PN sub forma

: P P1 P2 ... PN ;

Daca procedura P reprezinta actiunea pe care programul creat ar trebui sa o realizeze, construirea acestui program folosind mijloacele limbajului PAYA se reduce la detalierea secventiala a procedurilor P1, P2, ..., PN. Aceasta înseamnă că fiecare dintre aceste proceduri trebuie definită printr-o secvență de proceduri mai mici, care sunt apoi definite prin secvențe de proceduri și mai mici și așa mai departe, până când se obțin definiții care constau numai din primitive.

Acest tip de construcție de programe, pornind de la un scop dat și defalcând treptat procedurile utilizate până la nivelul instrumentelor de limbaj de bază, este cunoscut sub numele de programare de sus în jos. Este modalitatea principală de obținere a programelor în limbajul PARA pentru rezolvarea unor probleme individuale, bine definite. Opusul este programarea de jos în sus - construcția, bazată pe mijloacele de bază ale unui limbaj de sistem, a unor proceduri extinse treptat concentrate pe o anumită zonă problematică. În acest fel, limbajul este dezvoltat și adaptat unei aplicații specifice.

În ambele cazuri, structurarea atentă a programelor create este esențială: fiecare program și fiecare parte a programului trebuie să fie formată dintr-un număr mic de părți separate, fiecare dintre ele îndeplinește o funcție specifică și permite verificarea autonomă. În ceea ce privește limbajul PARA, aceasta înseamnă, în special, că definițiile procedurilor ar trebui să fie scurte: secvența definitorie, de regulă, nu trebuie să conțină mai mult de 5-7 termeni. Structurarea asigură că programul este înțeles, verificabil și modificabil și reduce semnificativ complexitatea creării și întreținerii acestuia.

Definiția exemplului de mai sus a procedurii P este una simplificată. De fapt, secvența definitorie poate conține ca membri nu numai nume de proceduri, ci și instrucțiuni (comenzi) constând din mai mult de un cuvânt. Numele unei proceduri, atunci când este utilizat în afara combinației cu alte cuvinte, este o comandă pentru a executa procedura desemnată de aceasta. Secvența numelui procedurii specifică faptul că aceste proceduri sunt executate în ordinea în care numele lor apar unul după altul (în ordine liniară). Pentru a specifica alte secvențe de execuție, RAYA oferă cuvinte speciale (prefixe) care prescriu execuția procedurilor numite în combinație cu acestea, în funcție de condiția specificată, precum și execuția repetată (ciclică) a procedurii.

De exemplu, secvența liniară P0 P1 face ca procedura P0 să fie executată și apoi procedura P1 să fie executată. Dacă procedura P1 nu trebuie executată întotdeauna, ci numai cu condiția ca rezultatul executării P0 să se obțină un număr pozitiv, atunci în loc de P1, scrieți comanda de execuție conform condiției: IF+ P1, adică. în loc de P0 P1 va fi P0 IF+ P1. RAYA include un set de prefixe condiționate care vă permit să exprimați eficient execuția după condiție, precum și o alegere a două, trei sau mai multe proceduri.

Executarea repetată a unei proceduri este specificată folosind prefixul RP. Astfel, comanda RP P provoacă executarea procedurii P din nou și din nou până când sunt create condiții în care EX conținut în corpul acestei proceduri este declanșat - ieșirea din buclă, după care se execută următoarea comandă în ordine liniară. Condiția pentru ieșirea din buclă poate fi, de exemplu, egalitatea unei variabile X la zero, care este exprimată ca:

Se spune că o procedură al cărei nume este inclus în definiția altei proceduri este imbricată în ea. O procedură imbricată, dacă nu este o primitivă, poate conține, la rândul său, proceduri imbricate, de exemplu. cuibărirea poate fi multiplă. În plus, regulile limbajului PARA nu interzic includerea în definiția unei proceduri a acesteia propriul nume sau numele unei proceduri care conține acest nume, adică RAYA permite recursiunea.

O procedură executată în mod repetat poate fi, de asemenea, imbricată într-o procedură executată în mod repetat. În acest caz, are loc imbricarea în buclă. PARA permite imbricarea mai multor bucle.

Secvență liniară de comenzi, imbricare, imbricare condiționată și ciclică a procedurilor - aceasta epuizează posibilitățile de construire a programelor în limbajul PARA. Lipsa, omogenitatea și naturalețea acestor mijloace este cheia ușurinței în stăpânirea și utilizarea limbajului. În același timp, este un limbaj de programare strict structurat, care asigură o reducere semnificativă a intensității muncii de dezvoltare și a fiabilității programului.

Proceduri și date

Tot ceea ce s-a spus până acum este o caracteristică a limbajului PARA ca mijloc de a prescrie acțiuni, de a construi acțiuni arbitrare dintr-un set finit de operații primitive. Cealaltă parte a limbajului constă în mijloace de reprezentare a obiectelor pe care se efectuează operații. acțiuni, mijloace prezentarea si organizarea datelor.

Un element de date extrem de simplu este un element cu două valori - un pic. Toate celelalte formate și tipuri de date sunt construite din biți. În limbajul RAYA, formatele de bază sunt octeți de 8 biți, cuvânt de 16 biți și cuvânt lung de 32 de biți. În funcție de operațiile efectuate asupra acestora, octeții, cuvintele și cuvintele lungi permit multe interpretări, adică. poate servi drept bază pentru tipuri variate date. În plus, ele sunt elementele de plecare pentru formarea de formate și tipuri compozite.

De fapt, PARADIS nu este nici simplu, nici tipuri compozite nu conține date - există doar formate de bază (octet, cuvânt, cuvânt lung) și instrumente pentru construirea de formate compuse din acestea: vectori și tablouri multidimensionale. În acest caz, aceiași octeți (cuvinte, cuvinte lungi), în funcție de operațiile efectuate asupra lor, sunt interpretați ca vectori de biți, sau ca numere întregi binare cu semn și fără semn, sau ca caractere ale alfabetului de intrare/ieșire etc. Tipurile de date și constrângerile și verificările asociate acestora pot fi introduse în extensii specifice problemei ale limbii.

În limbajul de bază, declararea numelor de date îndeplinește doar funcția de a oferi acces la date după nume: numele este asociat cu numărul de celule de memorie cerut de declarație și mecanismul de accesare a acestora. Operațiile de testare și transformare nu sunt aplicate direct datelor cu nume. Aceste operații sunt definite pe stiva de operanzi, care este o secvență de cuvinte lungi de 32 de biți (elemente de stivă) care este modificată dinamic prin adăugarea (împingerea) elementelor noi la capătul acesteia, precum și prin eliminarea elementelor de la același capăt ( ieșind din stivă). Articolele sunt eliminate în ordinea inversă în care au fost trimise: ultimul trimis este eliminat primul. Datele care urmează să fie testate sau convertite sunt trimise în stivă, unde se efectuează operațiunile prescrise pe acesta, după care rezultatele procesării pot fi eliminate din stivă.

De exemplu, dacă există o variabilă X declarată ca un cuvânt lung de 32 de biți, atunci doar două operații pot fi efectuate direct asupra acesteia:

1) împingerea valorii acesteia pe stivă, care apare automat de fiecare dată când este menționat numele X,

2) atribuirea lui echipei! X este valoarea ultimului element (de sus) scos din stivă.

Dacă, de exemplu, doriți să dublați valoarea lui X adăugându-l la sine, atunci puteți face acest lucru rulând următoarele comenzi una după alta:

Două copii ale valorii X vor fi împinse pe stivă, apoi comanda + le va elimina, le va adăuga și va împinge suma rezultată pe stivă, după care comanda! X va lua această sumă și va atribui valoarea ei variabilei X.

Înregistrarea obișnuită a exemplului de mai sus în forma X:=X+X pentru limbaje de nivel înalt este mai familiară programatorului, dar nu este o reflectare directă a secvenței de comenzi executate de procesor, ci este o un fel de formulă matematică. Acest lucru este convenabil la programarea sarcinilor de calcul, cu toate acestea, în limbajul de bază, corespondența neechivocă cu comenzile executate pare mai importantă, deoarece verificarea comandă cu comandă a programului se poate face direct în limbajul de programare și nu este nevoie să se facă. cunoașteți o altă limbă decât limba procesorului.

Dar un beneficiu deosebit de valoros al procesării datelor stivuite este că procedurile de testare și transformare pot fi definite și implementate independent de datele la care sunt aplicate. Operațiile de testare și conversie sunt formulate nu în raport cu identificatorii de date (sau denumirile constantelor și variabilelor, parametri formali), ci în raport cu elementele stivei, cărora trebuie să li se atribuie valori ale operanzilor până la momentul executării operațiunii. De exemplu, operația de adunare a două numere, efectuată cu ajutorul comenzii + (adăugați), constă în preluarea celor două elemente de sus (vârf și subvertix) din stivă ca adunări, calcularea sumei lor și împingerea acesteia pe stivă. Pentru a adăuga două numere, trebuie să le împingeți valorile pe stivă și să executați comanda +, rezultatul va fi în partea de sus a stivei.

O procedură de testare-transformare cu un număr arbitrar de parametri de intrare și de ieșire poate fi definită în acest fel pur și simplu ca o acțiune numită (fără o listă de parametri) efectuată pe o stivă care conține valorile argumentului, aranjate într-o ordine prescrisă și, după execuție, valorile rezultatului. Pentru a aplica o astfel de procedură unui anumit set de date specifice, trebuie să introduceți aceste date în secvența corespunzătoare în stivă. După ce le-a consumat, procedura își va lăsa rezultatele pe stivă (de asemenea, situată într-o anumită secvență).

Cu alte cuvinte, numele de proceduri în limbajul RAY sunt folosite în același mod ca semnele de operație și sunt în esență simboluri ale operațiilor cu un număr arbitrar de operanzi. În conformitate cu principiul de funcționare a stivei, operațiunile sunt scrise sub formă de postfix, adică. numele operațiunii este plasat după numele sau valorile operanzilor acesteia. De exemplu, dacă notăm operația de obținere a sumei a trei numere cu simbolul ++, atunci suma numerelor A, 5 și B se va exprima astfel:

Ar fi posibil să se stabilească reguli formale ale unui limbaj postfix și să fie ghidat de acestea atunci când scrieți programe, dar este mai ușor și mai de încredere pentru o persoană să se ocupe nu de reguli, ci de modelul procesorului de stivă, de exemplu. cu un model al mașinii pentru care sunt create programe și care le va executa. În cazul limbajului PARA, o astfel de mașină este un procesor DSSP - un set de echipamente și programe care implementează acțiunile prescrise în acest limbaj.

procesor DSSP

Din punct de vedere fizic, procesorul DSSP poate fi implementat sub forma unui microprocesor cu o arhitectură simplă și eficient programabilă care să permită rezolvarea în cel mai bun mod posibil a problemei echipamentelor software pentru microcalculatoare. Dar un astfel de microprocesor nu a fost încă creat și arhitectura sa trebuie emulată pe microcalculatoarele existente pentru a le îmbunătăți programabilitatea. Desigur, emularea este asociată cu costuri - necesită memorie și timp de calculator, dar în cazul emulării unui procesor DSSP, aceste costuri sunt relativ mici.

Din punctul de vedere al unui programator, o caracteristică a unui procesor este arhitectura acestuia, i.e. informații despre ce este un anumit procesor ca instrument de prelucrare a datelor, care sunt posibilitățile de prezentare a datelor la intrare și în interiorul procesorului, ce operațiuni de testare și conversie a datelor sunt disponibile, cum este organizată memoria proprie a procesorului, precum și accesul la memoria principală și externă, care sunt instrumentele de control a cursului programului, interacțiunea cu mediul extern, răspunsul la evenimente excepționale etc. Stăpânirea arhitecturii este conditie necesara programare semnificativă (informală), care reduce semnificativ numărul de erori și crește fiabilitatea programelor.

Legătura centrală a procesorului DSSP este stiva de operanzi deja menționată. De fapt, procesarea se face pe stivă și, de regulă, datele sunt trimise prin stivă. Comenzile individuale și secvențele scurte de comenzi de pe stivă pot fi executate prin trecerea lor la intrarea procesorului direct de la tastatura terminalului. În acest caz, procesorul DSSP simulează funcționarea unui calculator postfix. Numerele și codurile mnemonice de operare introduse de la tastatură sunt separate prin spații. Textul introdus apare ca o linie pe ecranul terminalului. Semnalul pentru sfârșitul intrării și comanda către procesor „Execută ordinea introdusă” este o apăsare de tastă , de asemenea notat , . Numerele care ajung la intrarea procesorului sunt stocate pe stivă, iar comenzile sunt executate pe stivă. Rezultatul calculului obținut în partea de sus a stivei poate fi copiat pe ecranul terminalului cu comanda. (punct).

De exemplu, pentru a evalua expresia (2-5)*3 și a afișa rezultatul obținut, introduceți:

2 5 - 3 * .

După apăsarea tastei procesorul produce rezultatul, astfel încât întreaga linie va arăta ca

* 2 5 - 3 * . -90

Un asterisc la începutul unei linii este emis de procesor ca un semnal că așteaptă intrarea.

În exemplul luat în considerare, procesorul a perceput și procesat numerele de intrare ca numere întregi zecimale. În realitate, la introducere, aceste numere au fost convertite în cod de complement binar, iar la ieșire, au fost convertite înapoi în sistemul zecimal. Procesorul DSSP permite, de asemenea, moduri de intrare/ieșire binar, octal și hexazecimal. Pentru a trece la modul dorit, trebuie să executați una dintre comenzile B2, B8, B10, respectiv B16.

Apăsarea tastelor provoacă trimiterea codurilor către intrarea procesorului, reprezentând caracterele indicate pe aceste taste (litere, cifre, semne de punctuație, simboluri de operare). Secvența de caractere introdusă formează un șir de intrare - un lanț de octeți care conține coduri de caractere, câte un octet pe caracter. Lungime maximașir de intrare - 80 de litri.

Atunci când procesează un șir de intrare, procesorul izolează cuvintele din acesta - combinații de caractere separate între ele prin spații și le interpretează. Dacă cuvântul procesat este numele unei operațiuni (procedură) sau date cunoscute de procesor, atunci procesorul efectuează acțiunile pe care acest nume ar trebui să le numească prin definiție. Dacă cuvântul nu este cunoscut de procesor, atunci acesta încearcă să-l interpreteze ca număr, ținând cont de modul I/O setat.

Numerele sunt cuvinte care constau din cifre acceptabile într-un sistem de numere dat și, probabil, care conțin un semn minus ca primă literă. În modul I/O hexazecimal, literele valide, împreună cu numerele, includ, de asemenea, literele latine A, B, C, D, E, F. Numărul primit este convertit în codul binar de complement doi și împins în stiva de operanzi ca un Cuvânt lung de 32 de biți. Mai mult, dacă valoarea numărului se află în afara intervalului de valori reprezentabile -2147483648: 2147483647, atunci este înlocuită cu o valoare comparabilă modulo 2**32 din acest interval.

În cazul în care cuvântul procesat nu este cunoscut de procesor și nu poate fi acceptat ca număr, procesorul afișează pe ecranul terminalului mesajul: „Nu știu”<обрабатываемое слово>" și așteaptă să fie introduse instrucțiuni suplimentare.

Introducerea datelor sub formă de text arbitrar (o secvență de octeți-literale) se face sub formă de literale text, care sunt text cuprins între ghilimele duble, de exemplu: „Literal text”. Sosirea unui text literal la intrarea procesorului face ca textul cuprins între ghilimele să fie scris în memoria principală sub forma unui lanț de octet-literali. În acest caz, adresa primului octet și numărul de octeți (lungimea textului) sunt împinse în stivă. Un text literal precedat de un punct este perceput de procesor ca o comandă pentru „a arăta textul dintre ghilimele pe ecranul terminalului”. De exemplu, trimiterea combinației de caractere „Fără memorie” la intrarea procesorului va face să apară pe ecran mesajul: Fără memorie.

Codul unui caracter individual este împins în stivă ca octet inferior al vârfului atunci când acest caracter este primit la intrarea procesorului împreună cu semnul # precedat de acesta. De exemplu, combinația de caractere #L va trimite codul literei L pe stivă, combinația de caractere #5 va trimite codul numărului 5. Comanda TOB pentru a trimite un octet către terminal afișează litera al cărei cod este conținut în octetul inferior al vârfului stivei.

Chiar și în modul de execuție directă a comenzilor, procesorul DSSP depășește cu mult capacitățile unui calculator convențional, oferind utilizatorului, pe lângă operațiunile de prelucrare a datelor, mijloacele de declarare a datelor denumite și de definire a procedurilor care pot fi apoi utilizate împreună cu operatii de baza. Declararea numelor de date și definirea procedurilor se face folosind comenzi speciale.

De exemplu, pentru a crea o variabilă de 16 biți numită, de exemplu, TEMP, ar trebui să tastați pe tastatură și să aplicați tasta la intrarea procesorului echipă

VAR TEMP

Împreună cu declarația, puteți atribui o valoare inițială variabilei, de exemplu, 0:

VAR TEMP 0! TEMP

Acum, sosirea numelui TEMP la intrarea procesorului va face ca valoarea curentă a acestei variabile să fie împinsă în stivă, iar atribuirea unei noi valori eliminate din stivă se poate face prin comandă! TEMP.

O definiție de procedură este introdusă prin comanda: (colon), care conține numele procedurii care se definește și un lanț definitoriu de comenzi cu o literă; (punct și virgulă) ca caracter final al definiției. Să demonstrăm definirea și utilizarea procedurilor folosind exemplul de calcul al factorialului unui număr natural N folosind formula

N!=N*(N-1)*(N-2)*...*2*1, adică. Înmulțirea N-1.

Pentru a obține rezultatul dorit, procedura FCT trebuie să înmulțească numărul dat N cu numere descrescătoare succesive, începând de la N-1 la 1, adică. doar de N-1 ori. În limbajul PARA, aceasta este programată prin executarea procedurii P t ori: DO P, unde P este numele procedurii, t este valoarea curentă din partea de sus a stivei, indicând de câte ori trebuie executată procedura P.

Să presupunem că înainte de a aplica procedura FCT, numărul N este împins pe stivă și este situat în partea de sus. Pentru a face procedura mai ușor de înțeles, să ne imaginăm multiplicatorul modificat al variabilei K:

Introducem definiția procedurii FCT sub forma:

FCT [N] ! K K K 1- DO F . [N];

Comentariile sunt date între paranteze drepte, reflectând starea curentă a stivei de operanzi. Echipă! K, care începe procedura definită, atribuie valoarea numărului N luat din stivă variabilei K. Apoi K este împins pe stivă de două ori și scăzând 1 din vârful stivei, numărul de execuții ale stivei repetate. se formează procedura F, egală cu N-1. Urmează comanda DO F, care specifică o buclă, la finalizarea căreia partea de sus a stivei va conține valoarea dorită a factorialului - N!. Echipă. (punct) imprimă o copie a acestei valori pe ecranul terminalului. Rămâne de definit o procedură F care modifică valoarea lui K scăzând 1 și înmulțește rezultatul parțial al calculului R conținut pe stivă cu K:

F [R] K 1- ! K[R]K*;

Corectitudinea ambelor proceduri este verificată prin executarea definițiilor lor comandă cu comandă, afișarea conținutului stivei de operanzi și a valorii variabilei K pe ecranul terminalului după fiecare comandă La finalizarea procedurii FCT, partea de sus a stivei trebuie conțin valoarea N!, iar valoarea variabilei K trebuie să fie egală cu 1.

Procedurile verificate și corectate (dacă au fost identificate erori în timpul procesului de verificare) sunt testate prin aplicarea acestora la valori individuale ale numărului N. Deoarece procedura F este încorporată în FCT, testarea acesteia este efectuată automat în timpul procesului de testare al acestuia din urmă. . Trebuie reținut că valorile rezultatelor nu trebuie să depășească numărul maxim pozitiv reprezentat în codul complement a doi ca un cuvânt lung de 32 de biți: 2147483647, i.e. FCT produce numai rezultate corecte pentru N=1, ..., 13.

Utilizarea FCT nu este diferită de utilizarea instrucțiunilor proprii ale procesorului: pentru a obține rezultatul, trebuie să setați valoarea operandului și să introduceți numele procedurii:

5 FCT 120

7 FCT 5040

Implementarea de mai sus a procedurii FCT a necesitat introducerea unei variabile auxiliare K, dar o procedură echivalentă din punct de vedere funcțional poate fi implementată fără o variabilă auxiliară, folosind operația C, care împinge o copie a vârfului acesteia pe stivă și operațiile E2 și E3, care schimbă partea superioară cu al doilea și, respectiv, al treilea element al stivei. Definiția acestei proceduri este următoarea.

: FCTA [N] C 1- C DO FA D . ;

: FA C E3 * E2 1- ;

Avantajul unei astfel de proceduri de „stivă pură” este că este complet autonomă: la fel ca operațiunile de bază ale stivei procesorului, se efectuează numai pe stiva de operanzi, fără a necesita altă memorie sau a provoca modificări altor componente ale procesorului.

Denumirile procedurilor definite și ale datelor declarate sunt introduse în dicționarul procesorului, care stabilește o legătură între aceste nume și obiectele denumite, adică cu corpuri de procedură situate în memoria principală și cu elemente din această memorie alocate pentru stocarea datelor declarate. Când procesează următorul cuvânt din fluxul de intrare, procesorul caută prin dicționar și, după ce a găsit un cuvânt potrivit în el, efectuează acțiunile asociate cu acest cuvânt. Dacă căutarea nu reușește, atunci, după cum sa menționat deja, se încearcă interpretarea numerică a cuvântului dat, iar dacă aceasta nu reușește, atunci apare un mesaj că cuvântul nu este cunoscut de procesor.

Ca rezultat al compilării unei definiții de procedură, numele acestei proceduri și pointerul (adresa) corpului său, care este o secvență de pointeri către proceduri și date care compun definiția, sunt introduse în dicționar. Cu alte cuvinte, reprezentarea internă a corpului unei proceduri se obține prin înlocuirea denumirilor de proceduri și date din definiția sa cu pointeri ai corpurilor corespunzătoare, care la rândul lor sunt aceleași secvențe de pointeri, iar în cazul primitivelor, lanțuri de comenzi ale mașinii. Numim această reprezentare internă a unui cod procedural de program.

Atunci când, împreună cu compilarea definiției procedurii P, sunt compilate și definițiile tuturor procedurilor imbricate necunoscute anterior procesorului, se formează o ierarhie completă de pointeri, făcând posibilă executarea procedurii P prin trimiterea numai a numelui acesteia la intrarea procesorului. . În același timp, nu are rost să stocați numele procedurilor imbricate compilate în legătură cu definiția lui P, dacă nu este nevoie să accesați aceste proceduri separat. Într-un număr de cazuri, se dovedește a fi recomandabil să închideți accesul la una sau alta parte a dicționarului, lăsând, probabil, capacitatea de a efectua doar unele proceduri.

Pentru a satisface astfel de cerințe, dicționarul este implementat ca un set de subdicționare, peste care sunt definite operațiuni care permit crearea și distrugerea subdicționarelor și părților acestora, ștergerea numelor, închiderea și deschiderea accesului la anumite subdicționare. Fiecare subdicționar are un nume care este folosit în comenzile aferente acestuia. Numele subdicționarelor trebuie să înceapă cu litera $, de exemplu: $PRIME, $EDIT, $FLOAT, $TEXTPROC, $GRAPHICS.

Subdicționarul $PRIME, care conține setul de bază de cuvinte DSSP, după pornirea procesorului, este deschis atât pentru accesul la cuvintele pe care le conține, cât și pentru adăugarea unor cuvinte noi. Cuvintele noi introduse în el, dacă este necesar, pot fi șterse împreună cu corpurile asociate cu ele folosind comanda FORGET $PRIME. După aceasta, posibilitatea introducerii în continuare a cuvintelor în acest subdicționar este asigurată prin executarea comenzii GROW $PRIME, care permite extinderea din nou a subdicționarului $PRIME, iar tot ce este introdus în el poate fi din nou șters cu comanda FORGET $PRIME etc. . În acest mod, DSSP este utilizat când se experimentează fragmente mici de programe, exemple individuale, estimări și, dacă este necesar, inclusiv cuvinte noi în subdicționarul $PRIME în ordinea dezvoltării limbajului sistemului.

În cazul creării unui program separat, ei își creează propriul subdicționar pentru acesta, iar acest lucru se realizează prin pornirea textului programului cu comanda

PROGRAM$<имя программы>

O persoană percepe această comandă ca un titlu, care ar trebui să fie urmat de un comentariu între paranteze drepte, care caracterizează în câteva cuvinte funcția implementată de program. Pentru procesor este echivalent cu o succesiune de comenzi

UITA $<имя>CREȘTE $<имя>

Prin urmare, fiecare sosire a textului programului la intrarea procesorului va determina ștergerea acestuia versiunea anterioarași va deschide subdicționarul astfel eliberat pentru intrare versiune noua program care poartă același nume. Acest lucru este convenabil atunci când faceți corecții la programul creat, precum și atunci când îl modificați în viitor.

Textul programului care se construiește nu este introdus în intrarea procesorului direct de la tastatură, ci este generat în buffer-ul editorului de text. Comanda E (Edit) setează modul de editare, în care cuvintele tastate pe tastatură nu mai sunt percepute de procesor ca comenzi care trebuie executate imediat, ci sunt pur și simplu text scris într-un buffer și afișat simultan pe ecran. Folosind taste speciale care controlează mișcarea indicatorului de poziție curentă (cursor) pe ecran, precum și comenzile de editare date prin apăsarea altor taste, textul introdus poate fi corectat și modificat, făcând ștergeri și inserări, mutându-și fragmentele dintr-un loc în altul. loc, etc.

La finalizarea introducerii și editarii textului, editorul este oprit prin apăsarea tastei E simultan cu (sau mai degrabă, cu tasta apăsată anterior) , iar sistemul intră în modul principal al comenzilor DSSP. O acțiune similară este cauzată de simpla apăsare a unei taste . În acest mod, conținutul buffer-ului editorului poate fi scos la intrarea procesorului cu comanda PF (PerForm - execute). În acest caz, toate comenzile conținute în text vor fi executate, în special comanda PROGRAM $<имя>va șterge $ introdus în subdicționar<имя>de la ultima dată când a fost executată această comandă, denumirile de date și proceduri, precum și corpurile corespunzătoare, redeschizând acest subdicționar pentru creștere. Comenzile de declarare a datelor și de definire a procedurii vor introduce numele pe care le introduc, împreună cu indicatorii către datele desemnate de acele nume și organele de procedură compilate conform definițiilor.

Odată ce încărcarea este completă, procedurile și datele sunt disponibile pentru referință prin numele de tastatură, iar corectitudinea programului poate fi verificată prin executarea procedurilor în ordine crescătoare, de exemplu. începând cu cei ale căror definiţii nu conţin proceduri netestate. Înainte de a începe verificarea, este necesar să vă asigurați că programul nu folosește nume nedefinite. Procesorul le afișează pe ecran folosind comanda UNDEF. Pentru a completa textul programului cu definiții ale acestor nume, precum și pentru a corecta alte erori detectate în timpul procesului de verificare, trebuie să utilizați comanda E pentru a apela editorul și a face modificarea corespunzătoare a textului programului sursă aflat în buffer-ul editorului. , apoi comutați procesorul în modul principal și încărcați conținutul buffer-ului cu comanda PF.

După verificarea și testarea programului, textul sursă al acestuia poate fi copiat din buffer-ul editorului pe disc folosind comanda OE f, unde f este numele fișierului în care programul va fi scris pe disc. În viitor, conținutul fișierului poate fi încărcat pe intrarea procesorului cu comanda LOAD f și, de asemenea, copiat în buffer-ul editorului ca o adăugare la textul din acesta folosind comanda IE f. În mod implicit, fișierele au extensia .DSP. Buffer-ul poate fi șters mai întâi cu comanda KE. De asemenea, este posibil să imprimați conținutul buffer-ului folosind comanda LPE.

După încărcarea unui program gata de execuție, este posibil să curățați subdicționarul creat pentru acesta $<имя>Comanda CLEAR $<имя>. Prin executarea acestei comenzi, procesorul elimină numele nefixate din subdicționarul numit, adică. toate numele, cu excepția celor ale căror definiții sunt precedate de un prefix fix:: (două două puncte). În acest caz, sunt șterse doar numele propriu-zise (intrări de dicționar), iar corpurile de procedură și datele asociate acestora sunt salvate și accesibile în timpul execuției programului prin link-uri interne stabilite în timpul compilării, dar nu mai sunt accesibile din exterior. Pentru a restabili capacitatea de a accesa din exterior, de exemplu, dacă trebuie să compilați o adăugare sau modificare, trebuie să descărcați din nou codul sursă al programului.

Numele pot fi făcute inaccesibile din exterior fără a le elimina din dicționar folosind comanda SHUT $<имя>, care blochează accesul la toate cuvintele subdicționarului numit în el. Deschiderea unui subdicționar pentru a-i folosi cuvintele se face cu comanda USE $<имя>. Există, de asemenea, o comandă ONLY $<имя>, care închide toate subdicționarele cu excepția celui numit și comanda CANCEL, care anulează această restricție. Comenzile enumerate vă permit să controlați utilizarea dicționarului în timpul compilării și să limitați setul de nume disponibile pentru utilizatorul programului la minimum necesar.

Căutarea unui nume în dicționar se face prin căutarea cuvintelor acestuia în ordinea inversă a ordinii în care au fost introduse în dicționar, adică. începând cu ultimul introdus. Prin urmare, pentru un nume definit de mai multe ori în dicționar, cea mai recentă definiție va fi valabilă. Dacă subdicționarul care conține această ultimă definiție este închis, atunci căutarea continuă până la prima intrare disponibilă din dicționar cu numele dat și se va folosi definiția indicată de acea intrare.

Câteva cuvinte despre intrarea și ieșirea datelor. După cum sa menționat deja, procesorul încearcă să interpreteze un cuvânt al programului executabil care nu se găsește în dicționar ca un număr și, dacă reușește, împinge echivalentul binar al acestui număr în stivă. Introducerea unui număr în stivă se poate face cu comanda TIN, care necesită introducerea numărului de intrare pe tastatură. Există, de asemenea, comenzi care fac ca un caracter introdus de la tastatură să fie împins pe stivă: TIB - cu afișaj, TRB - fără a afișa acest caracter pe ecran. În acest caz, codul caracterului este reprezentat de octetul mic al unui cuvânt de 32 de biți împins pe stivă, cei mai mari 3 octeți dintre care sunt egali cu zero.

Conținutul din partea de sus a stivei poate fi introdus ca număr sau ca literă. Comanda TON determină afișarea pe ecran a valorii numerice a subvertixului în câmpul de ieșire, a cărei lățime este specificată de vârf, în sistemul de reprezentare a numerelor stabilit la momentul executării acestuia. Comanda TOB afișează caracterul al cărui cod este conținut în octetul inferior din partea de sus a stivei. În ambele cazuri, rezultatul este însoțit de argumentele care sunt eliminate din stivă.

Procesorul DSSP are un aparat pentru întreruperi externe și interne (de comandă) și oferă următoarele mijloace pentru procesarea acestora. Procedura menită să gestioneze o întrerupere externă este definită în același mod ca o procedură normală, dar cu prefixul INT adăugat înainte de două puncte. Numele unei astfel de proceduri este asociat cu adresa vectorului de întrerupere cu comanda:

<адрес вектора>LEGĂTURĂ<имя процедуры>

O întrerupere de comandă este o operație numită care apelează o rutină de răspuns. Numele acestei operații este determinat de comanda TRAP, care îi asociază așa-numita procedură de răspuns final, care se execută dacă răspunsul final nu este înlocuit cu o altă procedură de răspuns folosind comanda ON sau EON. Toate cele trei comenzi au același format:

CAPCANĂ<имя вызова> <процедура реагирования>

PE<имя вызова> <процедура реагирования>

EON<имя вызова> <процедура реагирования>

Procedura asociată numelui apelului de către instrucțiunea EON este executată cu o ieșire preliminară din corpul procedurii care conține instrucțiunea EON și cu valoarea pointerului stivei de operanzi care exista la momentul executării EON.

Sintaxa limbajului RAYA

Alfabetul limbii RAY include latină și rusă, litere mici și majuscule, numere zecimale, caractere matematice și alte caractere speciale. Elementele (membrii) alfabetului se numesc litere. Reprezentarea externă a unei litere este imaginea ei imprimată ( semn imprimat). În interiorul procesorului DSSP, fiecare caracter imprimat este reprezentat de un octet, a cărui valoare este codul binar al acestui caracter. Conversia reprezentării externe în internă și invers este efectuată de un dispozitiv de intrare/ieșire (tastatură, afișaj, imprimantă). Pentru comoditate, valoarea numerică a codului este exprimată în sisteme zecimal, hexazecimal sau octal, denumind numărul corespunzător literă de cod zecimal, hexazecimal sau octal.

Toate obiectele limbajului RAYA sunt construite din caractere și reprezintă lanțuri liniare de caractere de lungime finită, numite cuvinte. Separatorul cuvintelor care urmează unul altuia este un caracter neimprimabil (spațiu). Un șir de spații este echivalent cu un singur spațiu. În plus, funcția de separator de cuvinte este îndeplinită de comanda „Mergeți la începutul liniei următoare”, indicată pe tastaturile dispozitivelor de intrare prin simbolul sau și, împreună cu litere, având o reprezentare internă ca un cod octet. Astfel, nu este nevoie de separarea spațiilor la începutul și la sfârșitul liniei.

Exemple de cuvinte: CLEAR NOP STACK2 & 1+ -366 X Probe.

Procesorul DSSP distinge cuvintele după primele șapte litere, recunoscându-le prin comparație poliliterală cu cuvintele din dicționarul său. Dicționarul conține cuvinte care sunt nume (denumiri) ale operațiilor proprii ale procesorului, numite operații de bază sau primitive, și pot fi completate cu nume de obiecte (date, proceduri) definite de utilizator. Astfel, cuvintele conținute în dicționar sunt fie nume de acțiuni (operații, proceduri), fie nume de date (constante, variabile, tablouri).

Când un cuvânt identificabil nu este în dicționar, procesorul încearcă să-l atribuie unuia dintre următoarele cazuri:

    literal numeric, adică o succesiune de numere, eventual începând cu semnul minus, de exemplu: 0, 4096, -25;

    literal literal: un cuvânt care începe cu caracterul #, care face ca procesorul să primească literalul imediat următor ca un cod dat, de exemplu: #A - literal majuscul Literă latină A, #5 - literal al numărului 5, # - literal al spațiului, ## - literal al caracterului #;

    text literal: text arbitrar cuprins între ghilimele duble și separat prin delimitatori de cuvinte, de exemplu: „Text”, „Fișier de intrare N3”;

    comandă pentru afișarea unui mesaj text: textul mesajului afișat, delimitat în stânga de combinația de caractere punct-ghilimele duble și ghilimele duble în dreapta și separat prin delimitatori de cuvinte, de exemplu: „Stiva este goală”;

    comentariu: text arbitrar cuprins între paranteze pătrate și separat prin delimitatori, de exemplu: .

Literale și comanda de afișare a unui mesaj pe afișaj acționează ca obiecte ale limbajului DSSP împreună cu cuvintele identificate din dicționar, în timp ce comentariile sunt complet ignorate de procesorul DSSP - sunt destinate unei persoane, nu unei mașini. Dacă cuvântul nu se găsește în dicționar și nu are legătură cu construcțiile enumerate, procesorul afișează mesajul: „Nu știu<неопознанное слово>".

Datorită semnificației speciale atașate literelor #, „și combinația”. la începutul unui cuvânt, adică după separator, precum și litera „ înainte de separator, acestea nu trebuie folosite în pozițiile specificate în cuvintele definite pentru a fi incluse în dicționar.

Secvența de cuvinte la intrarea procesorului este interpretată ca o secvență de instrucțiuni executate de procesor. Există trei tipuri de cuvinte:

1) efectuat independent, adică reprezentarea comenzilor cu un singur cuvânt (monocuvinte);

2) efectuată împreună cu unul sau mai multe cuvinte ulterioare, i.e. fiind cuvintele inițiale (prefixele) ale comenzilor cu două, trei sau mai multe cuvinte;

3) precedarea unei comenzi ca clarificare sau indicație modul special execuție (prefixe).

Monocuvintele includ literale, nume de date, majoritatea operațiunilor I/O, testare și conversie a datelor pe stivă și proceduri definite de utilizator. De exemplu: 1987 - literal numeric, #5 - literal al numărului 5, „Lista schemei” - literal text, LUNGIME - nume variabilă, TOB, NEG, +, &,<, = - имена (обозначения) операций, SORT, CONVERT, ЧИСТКА, СНЯТЬ - имена процедур пользователя.

Prefixele sunt inerente comenzilor pentru descrierea datelor și definirea procedurilor, precum și manipularea datelor cu nume, execuția condiționată și repetată a procedurilor și gestionarea unui dicționar. Exemple de comenzi cu prefixe:

VAR SUM - creați o variabilă SUM,

: ODD [x] 1 & ; - creați o procedură IMPAR care înlocuiește un număr impar cu 1, un număr par cu 0,

0 X - atribuiți valoarea 0 variabilei X,

BR+ P1 P2 - dacă valoarea vârfului său luată din stivă este pozitivă, atunci executați P1, în caz contrar executați P2,

RP CHECK - efectuați procedura de VERIFICARE din nou și din nou,

USE $REAL - deschideți subdicționarul $REAL pentru utilizare.

De obicei, un prefix specific necesită un anumit număr de cuvinte după el. Deci, în exemplele tocmai date, prefixele VAR, !0 și USE necesită fiecare câte un cuvânt, iar prefixul BR+ necesită două cuvinte. Cu toate acestea, prefixul: (coloană) vă permite să creați o comandă de orice lungime, începând cu trei cuvinte. Sfârșitul comenzii este cuvântul; (punct şi virgulă). O lungime arbitrară este de asemenea caracteristică comenzii de descriptor constant CNST A1 ... AJ ; iar procedura de selecție multiplă comanda BR A1 P1 ... AJ PJ ELSE PN.

Prefixele sunt cuvinte speciale care, atunci când sunt adăugate în fața unei comenzi, îi modifică conținutul sau definesc un mod special de execuție. De exemplu, comanda VAR X fără prefix este o instrucțiune pentru a crea o variabilă X pe 16 biți. Dacă atașați prefixul BYTE la aceasta, obțineți comanda BYTE VAR X, care vă indică să creați o variabilă pe 8 biți. variabilă (octet) numită X. Dacă utilizați un prefix LONG, atunci obținem LONG VAR X - o instrucțiune pentru a crea o variabilă de 32 de biți numită X.

Un prefix de alt tip, și anume:: (două două puncte) face ca rezultatul comenzii să fie rezistent la procedura CLEAR, care elimină cuvintele libere din dicționar. Numele introduse în dicționar în timpul construcției programului de comenzile de descriere a datelor și definirea procedurii pot fi eliminate din dicționar după ce programul a fost creat și testat, cu excepția câtorva care sunt necesare pentru menținerea programului terminat. Îndepărtarea se efectuează cu comanda CLEAR $<имя подсловаря>, care indică ștergerea subdicționarului asociat programului, păstrând în el doar acele cuvinte ale căror definiții conțin prefixul ::. Exemple de comenzi care generează cuvinte de neșters:

:: BYTE CNST LITCODE # #0 #A ;

:: : MOD / [int(a,b),res(a,b)] E2 D [res(a,b)] ;

După cum arată al doilea exemplu, care conține prefixele :: și BYTE, o comandă poate avea mai mult de un prefix.

Astfel, o comandă într-un DSSP poate fi fie un cuvânt (monocuvânt), fie o expresie (expresie), începând cu un prefix și care conține numărul de cuvinte setat pentru acest prefix, iar dacă prefixul permite un număr arbitrar de cuvinte, atunci având un cuvânt limitativ la sfârșit sau poate fi o frază completată în față cu cuvinte speciale cu prefix.

Limbajul de bază DSSP nu conține construcții sintactice mai complexe decât comanda și, în general, nu conține alte construcții decât cele discutate mai sus. Chiar și lucruri atât de indispensabile în limbajele de programare precum expresia și funcția sunt absente în limbajul de bază și pot fi introduse, dacă este necesar, numai în timpul dezvoltării acestuia.

Un program într-un limbaj de bază este pur și simplu o colecție de comenzi executate în ordinea în care apar în text. Mai mult, fiecare comandă, cu excepția celor care conțin doar primitive, în timpul executării sale implică o succesiune de comenzi care definesc cuvintele incluse în ea. Comenzile implicate pot conține, la rândul lor, cuvinte care denotă lanțuri de comenzi, care pot conține, de asemenea, cuvinte care se referă la lanțurile lor asociate etc. până la nivelul în care comenzile conţin doar primitive.

Descrierea generală a limbajului PARA, care a format conținutul acestui capitol, a fost dedicată caracteristicilor structurii acestui limbaj și setului de bază (inițial) al comenzilor sale, care este un set de comenzi încorporate (primitive) a procesorului DSSP. Dezvoltarea ulterioară a limbajului și creșterea corespunzătoare a capabilităților procesorului se realizează prin introducerea de noi proceduri, comenzi, formate și tipuri de date construite folosind instrumente de bază. De regulă, o astfel de dezvoltare este de natură orientată către probleme și se realizează sub formă de pachete de proceduri încărcate pe intrarea procesorului în plus față de sistemul de bază.

Pe de altă parte, sistemul de bază poate fi completat cu mijloace speciale implementate pe baza acestuia pentru a crește eficiența mașinii programelor DSSP. Aceste caracteristici includ capacitatea de a defini proceduri individuale direct în codul de comandă al mașinii utilizate. Metoda de definire a unei proceduri nu are niciun impact asupra utilizării sale ulterioare: numele tuturor procedurilor sunt introduse într-un dicționar comun și sunt complet egale. O serie de programe de bibliotecă vă permit să utilizați proceduri sau programe întregi scrise în alte limbi.

Descrierea operațiunilor și comenzilor

Operații efectuate pe stivă

Stiva de operanzi este unul dintre elementele principale ale arhitecturii procesorului DSSP. Majoritatea instrucțiunilor procesorului folosesc stiva, consumând operanzii de care au nevoie din el și împingând rezultatele pe el. Interpretarea datelor de pe stivă depinde de esența problemei care se rezolvă, adică, în cele din urmă, este responsabilitatea programatorului. Datorită faptului că o valoare introdusă în stivă își pierde de fapt numele, este dificil să se determine din textul programului la care operanzi se aplică o anumită operație și care sunt rezultatele acesteia. Prin urmare, comentariile sunt folosite pentru a indica în mod explicit operanzii și rezultatele procedurilor în limbajul RAYA. În acest caz, nu este necesar (și nu întotdeauna posibil) să descrieți întregul conținut al stivei. Este absolut necesar să comentați partea superioară a stivei, care este afectată de procedura efectuată pe aceasta, deoarece fără aceasta, claritatea programului se pierde și verificarea acestuia devine dificilă.

Pentru a obține uniformitatea programului, aceste comentarii ar trebui scrise ținând cont de câteva reguli simple. Ca orice comentariu, descrierea datelor de pe stivă este inclusă între paranteze drepte. Această descriere este o listă de operanzi care se află pe stivă la un anumit punct al programului. Fiecare element de listă caracterizează conținutul unei poziții de stivă este folosită o virgulă ca delimitator. Valorile poziției stivei sunt listate de la stânga la dreapta, începând cu cel mai adânc element și terminând cu partea de sus a stivei. Descrierea unui operand individual poate fi un număr, un nume, o expresie sau orice altă intrare semnificativă care explică semnificația unei valori situate pe stivă. Uneori există mai multe valori posibile pentru o poziție de stivă. În acest caz, valorile sunt enumerate separate printr-o bară oblică.

Iată un exemplu de comentariu care reflectă starea stivei de operanzi:

[adresă de început, N+1,1/0]

În punctul din program în care se află acest comentariu, stiva de operanzi trebuie să conțină cel puțin trei poziții, cu un 1 sau 0 în partea de sus, o valoare numerică egală cu N+1 în partea de sus și un număr dedesubt. , interpretată ca adresa de pornire.

Pentru comoditatea indicarii pozitiei necesare a stivei, vom folosi conceptul de adancime. Vom presupune că vârful stivei se află la adâncimea 1, partea superioară la adâncimea 2 etc. În special, valoarea indicată în exemplu ca „start.address”. se află la adâncimea 3.

Vom începe studiul limbajului de bază DSSP cu comenzi pentru împingerea valorilor în stivă. Cea mai simplă (și cel mai frecvent utilizată) comandă de acest tip este un literal numeric, adică o indicație explicită a unei constante care ar trebui să fie împinsă în stivă. De exemplu, dorim să împingem numerele 28, -5 și 11 în stivă. Pentru a face acest lucru, trebuie să introducem linia de la tastatură:

28 -5 11 și apăsați tasta (retur transport). Procesorul va recunoaște numerele introduse și le va împinge unul câte unul pe stivă, astfel încât partea de sus va fi 11. Pentru a verifica acest lucru, trebuie doar să tipăriți valoarea vârfului stivei pe ecranul de afișare. Pentru a face acest lucru, utilizați comanda DSSP cu numele. (punct). Tastând litera „punct” pe tastatură și apăsând , primim răspunsul pe ecran: 11, care corespunde ultimei valori introduse în stivă. Executarea „punct” din nou produce același rezultat - această comandă redă doar vârful fără a schimba starea stivei.

Pentru a afișa pe ecran întregul conținut al stivei, DSSP are comanda .. (două puncte). După ce l-am executat, obținem linia pe ecran:

După cum puteți vedea, forma imprimării urmează convențiile pentru comentarea stării stivei (cu excepția faptului că se folosește un spațiu în loc de virgulă). Comanda .. nu modifică conținutul stivei.

Un cuvânt de 32 de biți (4 octeți) este utilizat pentru a reprezenta o poziție de stivă în memoria mașinii numerele sunt reprezentate în complementul a doi. În consecință, procesorul DSSP poate percepe corect numai numere întregi situate în intervalul de la -2147483648 la 2147483647. Dacă numărul introdus nu poate fi reprezentat de 32 de biți (ținând cont de semn), atunci cei mai semnificativi biți care nu se potrivesc sunt eliminați. .

În exemplele luate în considerare, sa presupus că procesorul DSSP este în modul de intrare/ieșire zecimal. Pentru a seta acest mod în limba PARA există o comandă B10.

În multe sarcini, este necesar să se interpreteze datele procesate nu ca numere, ci ca coduri binare, adică vectori de biți cu 32 de componente. DSSP are capacitatea de a lucra cu coduri prezentate în sisteme de numere binare, octale sau hexazecimale. Pentru a seta modul dorit, este suficient să executați una dintre cele trei comenzi: B2, B8 sau B16, după care procesorul va accepta și imprima toate codurile introduse în sistemul de numere specificat.

Această caracteristică poate fi folosită pentru a converti numere zecimale în sisteme numerice cu bazele 2, 8 și 16. De exemplu, pentru a converti numărul 29 trebuie să introduceți și să executați următoarea linie:

B10 29 B2. B8. B16. Ca rezultat, procesorul va afișa o serie de numere pe ecran: 00000000035 0000001D care sunt reprezentări ale numărului zecimal 29 în cele trei sisteme numerice specificate. Rețineți că codurile sunt imprimate în reprezentarea mașinii lor, adică cu zerouri înainte și fără semnele „+”, „-”. La executarea liniei B10 -2 B8 . va produce numărul 37777777776, care este reprezentarea octală a complementului a două de -2.

Când lucrați cu coduri hexazecimale, pot apărea coliziuni între literalele numerice și numele comenzilor procesorului DSSP. De exemplu, cuvântul B8 în modul I/O hexazecimal poate fi interpretat ca o comandă în mod octal și ca o constantă hexazecimală. Pentru a evita ambiguitatea, ar trebui să începeți literalele numerice cu un zero nesemnificativ, de exemplu 0B8.

Baza sistemului de comandă al procesorului DSSP este operațiunile de conversie a datelor situate pe stivă. Regula generală care guvernează operarea acestor operații este că fiecare operație consumă (elimină) operanzii de care are nevoie din stivă și împinge valorile rezultatului (dacă există) în locul lor.

Să luăm în considerare instrucțiunile procesorului care implementează patru operații aritmetice: adunarea, scăderea, înmulțirea și împărțirea numerelor întregi. Pentru a le reprezenta în limba PARADIS, se folosesc cuvintele: +, -, * și respectiv /. Pentru a obține suma a două numere de pe stivă, de exemplu 123 și 45, trebuie să împingeți aceste numere pe stivă și să executați comanda +. Pentru a face acest lucru, introduceți pur și simplu următoarea linie de la tastatură (presupunând că este setat modul de intrare/ieșire zecimal):

123 45 +

Dacă acum afișați conținutul stivei pe ecran (folosind comanda ..), veți vedea rezultatul adăugării:

Operația de înmulțire comutativă funcționează în mod similar.

Când se efectuează operații necomutative de scădere și împărțire, subvertexul stivei este luat ca minuend (divizibil), iar vârful este luat ca subtrahend (divizor). De exemplu, pentru a calcula diferența 151-68, trebuie să executați linia:

151 68 -

Programul pentru efectuarea unei operații aritmetice în limbajul PARA se caracterizează prin faptul că operația se află după operanzii corespunzători. Această notație a expresiilor aritmetice se numește notație postfixă (sau inversă poloneză) și este utilizată pe scară largă în microcalculatoarele de stivă. De exemplu, trebuie să calculăm valoarea expresiei aritmetice ((127+81)*15-(31+117)*21)*3

În notația postfix, această expresie va arăta astfel:

127 81 + 15 * 31 117 + 21 * - 3 *

Această linie (în care cuvintele sunt separate unele de altele prin spații) este un program gata făcut pentru calcularea expresiei noastre de către procesorul DSSP.

Diviziunea / comanda diferă de alte operații aritmetice prin faptul că rezultatul său este două valori - coeficientul și restul. Coeficientul ajunge în partea de jos a stivei, iar restul în partea de sus. Un cot este negativ dacă dividendul și divizorul au semne diferite. Restul are întotdeauna semnul dividendului. Iată câteva exemple de utilizare a comenzii de divizare.

125 7 / [-17,-6] / / /

La efectuarea calculelor pot apărea situații de eroare: depășire și împărțire la zero. Procesorul DSSP nu reacționează la ele în niciun fel (în special, la împărțirea la zero, conținutul stivei nu se modifică), iar controlul asupra utilizării corecte a operațiunilor revine programatorului.

Când programați, de multe ori trebuie să creșteți sau să micșorați valoarea unei valori cu 1 sau 2. Au fost introduse comenzi speciale în limbajul PARA care efectuează acțiuni specificate în partea de sus a stivei. Ele sunt desemnate prin cuvintele: 1+, 1-, 2+, 2-. Executarea acestor comenzi echivalează cu împingerea constantei necesare (1 sau 2) pe stivă și apoi efectuarea operației aritmetice necesare (+ sau -). De exemplu, 2+ este echivalent cu perechea de cuvinte 2+. Introducerea acestor comenzi în limbaj a fost condusă de considerente de eficiență.

De asemenea, pentru a crește eficiența, limbajul de bază al procesorului DSSP conține comenzile T0 și T1, care înlocuiesc valoarea din partea de sus a stivei cu 0 și respectiv 1, indiferent de ce valoare era în vârf înainte de comanda specificată. Exemple:

Comenzile NEG, ABS și SGN sunt, de asemenea, concepute pentru a funcționa cu date numerice. Comanda NEG inversează semnul vârfului stivei, ABS înlocuiește valoarea vârfului stivei cu modulul său, SGN consumă o valoare numerică din vârful stivei și plasează semnul numărului extras în locul său: -1 - dacă numărul este negativ, 1 - dacă este pozitiv, 0 - dacă este egal cu zero. De exemplu:

5 NEG [-5] ABS SGN

Comenzile limbajului de bază MIN și MAX vă permit să găsiți minimum și maxim de două numere întregi. Operanzii acestor instrucțiuni sunt două numere situate în partea de sus și sub partea de sus a stivei. Comanda MIN lasă numărul minim de parametri pe stivă, MAX - maximul dintre ei. De exemplu:

5 0 15 MIN [-5.0] MAX

Pentru a găsi minimul (maximum) de trei numere din stivă, trebuie doar să utilizați comanda MIN (MAX) de două ori:

MIN MIN [-2]

Comanda SEG verifică dacă numărul conținut în partea de sus a stivei se încadrează în intervalul specificat de la a la b (inclusiv granițele) și lasă un semn pe stivă ca rezultat: 1 dacă numărul este în interval și 0 dacă nu:

SEG [semn] de exemplu:

Pe lângă comenzile axate pe lucrul cu date numerice, setul de comenzi al procesorului DSSP include o serie de operațiuni concepute pentru a converti coduri pe 32 de biți. Aceste operații tratează un element de stivă ca un vector de biți de 32 de componente, ale cărui componente sunt numerotate de la dreapta la stânga, astfel încât bitul din stânga este numerotat cu 31, iar bitul din dreapta este numerotat cu 0. Numerotarea descrescătoare a componentelor urmează numerotarea biți de cuvinte mașină adoptați pentru multe microprocesoare.

Comenzile efectuate pe vectori de biți includ în principal operații de algebră booleană pe biți:

    inversarea pe biți a vârfului stivei INV, schimbând valoarea fiecărui bit din partea de sus, adică înlocuirea 0 cu 1 și 1 cu 0;

    conjuncție pe biți a vârfului și a subvertixului stivei &, setând al-lea bit al rezultatului, i=31,30,...,0, la valoarea 1 dacă i-lea biți ai ambilor operanzi sunt egali cu 1, iar în alte cazuri setarea i-lea bit egal cu 0;

    disjuncția pe biți a vârfului și subvertixului stivei &0, setând i-lea bit al rezultatului, i=31,30,...,0, la valoarea 0 dacă i-lea biți ai ambilor operanzi sunt egali cu 0, iar în alte cazuri setarea i-lea bit egal cu 1;

    adăugare pe biți (neechivalență) „+” a unui vârf și a unui subvertix, setarea i-lea bit al rezultatului la 0 dacă i-lea biți ai ambilor operanzi au aceleași valori și setarea i-lea bit al rezultă la 1 dacă valorile biților i ai operanzilor sunt diferite.

525 INV 722 & 136 & 0 325 „+”

Conjuncția biți este adesea folosită pentru a reseta (șterge) biții unui cuvânt. Pentru a face acest lucru, ei efectuează o conjuncție a cuvântului original cu o mască care conține zerouri în acei biți care trebuie șters și cele în biții rămași. De exemplu, dacă trebuie să resetați biții de la 3 la 5 într-un cuvânt X, trebuie să efectuați conjuncția sa pe biți cu masca 37777777707. Pentru X=235 obținem:

Disjuncția pe biți poate fi utilizată pentru a pune combinația dorită de biți într-un grup de biți de cuvinte șters anterior. De exemplu, trebuie să puneți combinația binară 010 în biții de la 3 la 5 ai cuvântului rămas pe stivă ca rezultat al ultimului exemplu. Acest lucru se poate face astfel:

Operațiile de manipulare a biților includ, de asemenea, comenzi de schimbare logică:

    shift stânga SHL - fiecare bit din partea de sus a stivei, începând cu al 31-lea, ia valoarea următorului în ordine descrescătoare, iar ultimul bit zero ia valoarea 0;

    dreapta shift SHR - fiecare bit din vârful stivei, începând de la 0, ia valoarea următorului în ordine crescătoare, iar al 31-lea bit ia valoarea 0;

    deplasare la SHT de sus - elementul de sus este scos din stivă și tratat ca un număr întreg N, indicând câte deplasări și în ce direcție ar trebui făcute în partea de sus a stivei: când N>0 se face o deplasare la stânga , când N<0 - вправо.

B8 125 SHR SHL -2 SHT

Operațiile de schimbare la stânga pot fi folosite pentru a înmulți numerele cu 2 până la puterea lui N, unde N este un număr natural care determină numărul de schimburi. De exemplu, înmulțirea numărului -5 cu 8 se poate face prin deplasarea numărului de 3 locuri la stânga:

B10 -5 3 SHT [-40]

Trebuie luată în considerare posibilitatea revărsării.

Deplasarea la dreapta poate fi folosită ca împărțire cu 2 la puterea lui N numai pentru numere pozitive, deoarece bitul cel mai semnificativ (semn) este setat la zero în timpul deplasărilor la dreapta. De exemplu:

întrucât

Comenzile pentru deplasarea ciclică a vârfului stivei cu 1 bit la ROR dreapta și ROL stânga sunt similare cu comenzile de schimbare logică, cu excepția faptului că bitul cel mai exterior împins nu dispare, ci este împins în spațiul liber de la capătul opus al Cuvânt lung de 32 de biți. De exemplu (numere hexazecimale):

Comenzile procesorului DSSP SWB și SWW sunt, de asemenea, destinate procesării codurilor binare. Funcția SWB este de a schimba octeții jumătății de ordin inferior din partea superioară a stivei, iar funcția SWW este de a schimba jumătățile din partea superioară a stivei. Să ilustrăm cum funcționează aceste comenzi folosind modul I/O hexazecimal (în acest mod, fiecare octet este reprezentat de două cifre hexazecimale):

B16 0ABCD SWB SWB

0ABCDEF12 SWW SWB

Comenzile de manipulare a stivei joacă un rol important în limbajul PARA. Ele nu modifică valorile datelor aflate pe stivă, ci doar le schimbă locația, facilitând accesul operanzilor aflați adânc în stivă.

Există trei comenzi pentru ștergerea elementelor stivei: D, DD, DS (Drop). Comanda D elimină un element (de sus) din stivă, DD elimină două elemente, de exemplu:

D DD D DS elimină toate elementele din stivă (șterește stiva):

Comanda pentru a copia partea de sus a stivei C (Copiere) împinge o copie a valorii curente a vârfului său în stivă. Acest lucru este echivalent cu duplicarea elementului superior al stivei: vechiul vârf devine subvertix, iar copia sa devine noul vârf. Exemplu:

Să arătăm utilizarea acestei comenzi folosind exemplul de calcul al polinomului p(x)=3*x**2+4*x-5 folosind schema lui Horner: p(x)=(3*x+4)*x- 5. Presupunem că valoarea x este conținută în partea de sus a stivei.

[x] C 3 * 4 + * 5 -

Alături de comanda de copiere a vârfului stivei, limbajul PARA are și comenzile C2, C3, C4, care copiază elemente situate la adâncimile 2, 3, 4. Lucrarea lor poate fi explicată prin următoarele exemple:

C2 C4

Există, de asemenea, o comandă CT pentru a copia un element situat la o adâncime specificată în partea de sus a stivei. Când efectuează CT, procesorul scoate elementul superior din stivă, folosește valoarea acestuia ca un indicator al adâncimii elementului copiat și împinge o copie a acestuia din urmă pe stivă. Astfel, copierea unui element situat la adâncimea 5 este specificată de o pereche de 5 instrucțiuni CT, executând care procesorul va împinge numărul 5 pe stivă și apoi va executa instrucțiunea CT. Executarea CT cu parametrii 1, 2, 3, 4 este echivalentă cu comenzile C, C2, C3, respectiv C4.

Comenzile de schimb E2, E3, E4 (Schimb) rearanjează primul element (de sus) al stivei, respectiv, cu al 2-lea, al 3-lea, al 4-lea, adică cu elementul situat la o adâncime de 2, 3, 4. De exemplu:

E3 E2

Pentru a schimba la o adâncime mai mare, utilizați comanda ET, care, la fel ca CT, folosește valoarea vârfului stivei ca indicator al adâncimii elementului care este schimbat cu primul element. De exemplu:

5 ET

Comanda ET cu parametrii 2, 3, 4 este echivalentă cu comenzile E2, E3, E4.

Pentru a ilustra utilizarea comenzilor de copiere și partajare, luați în considerare o sarcină de învățare. Există trei numere pe stivă. Necesar să fie primit pe stivă: . Puteți sugera următorul program, al cărui sens este clar din comentarii.

C3 C3 C3+

E4+E4

Acest exemplu arată cât de important este rolul comentariilor, reflectând starea stivei de operanzi.

În programe, este adesea necesară compararea valorilor numerice între ele și efectuarea diferitelor proceduri în funcție de rezultatele comparației. Limbajul RAYA are comenzi de comparare<, =, >. Ele sunt definite peste numere și produc valorile numerice 0 și 1 ca rezultat< потребляет из стека два элемента и засылает в стек число 1, если значение нижнего элемента оказалось меньше значения верхнего, а в противном случае засылает 0. Например, в результате выполнения последовательности 5 -20 < в стек будет заслан 0. Команда = засылает 1 в случае равенства потребленных ею элементов. Команда >trimite 1 când elementul de jos este mai mare decât elementul de sus. Pentru a programa comparații nestricte (mai mici sau egale, mai mari sau egale), se folosește instrucțiunea NOT, care înlocuiește valoarea din partea de sus a stivei care nu este egală cu zero cu zero și egală cu zero cu unu. De exemplu, evaluarea expresiei logice x>=5, unde x este un număr situat în partea de sus a stivei, poate fi specificată după cum urmează:

[x] 5< NOT

O extindere suplimentară a capacităților de programare a condițiilor este asigurată de utilizarea, împreună cu comenzile de comparare, a operațiilor logice de conjuncție & (ȘI logic) și disjuncție &0 (SAU logic). De exemplu, doriți să obțineți 1 pe stivă dacă numărul x de la vârf aparține semisegmentului C 5< NOT C2 10 <

&E2 2 = &0

Controalele programului în funcție de rezultatele comparației vor fi discutate mai târziu.

Definirea Procedurilor

Ca tehnică de programare de bază, DSSP oferă utilizatorului abilitatea de a defini secvențe numite de operații numite proceduri. De exemplu, trebuie să calculați valorile trinomului pătratic 3*x**2-4*x+9 pentru valorile date ale lui x. În acest caz, ar trebui să definiți o procedură care să implementeze formula trinomului și să trimită rezultatul către terminal, apoi să aplicați această procedură la anumite valori ale lui x. Procedura necesară, să o numim PX, este definită după cum urmează: PX [x] C 3 * 4 - * 9 + . D; Colonele indică o operațiune „definiți procedura”, cu numele procedurii urmat de două puncte după un spațiu de separare. Secvența definitorie de comenzi (corpul procedurii) se află după numele procedurii și se termină cu punct și virgulă. Pe scurt, procedura este definită sub forma:

: <имя процедуры> <тело процедуры> ;

Limbajul RAYA necesită comentarea stării stivei de operanzi la începutul și la sfârșitul unei proceduri. În corpul procedurii, comentariile sunt plasate la discreția programatorului în locuri greu de înțeles.

Comentariile îi ajută pe oameni să înțeleagă și să utilizeze procedura; procesorul pur și simplu ignoră orice este inclus în paranteze. Prin urmare, la introducerea definiției unei proceduri individuale din terminal, comentariile pot fi omise.

După ce se introduce definiția procedurii și se apasă tasta procesorul este informat despre sfârșitul intrării, pe ecranul terminalului apare un asterisc, semnalând executarea comenzii „define procedura” și disponibilitatea procesorului de a continua dialogul. Acum puteți aplica procedura PX la valorile x specificate de la tastatură, de exemplu, la 2, 3, 4 (produs de procesor este subliniat):

* 2 PX 13

*3 PX 24

* 4 PX 41

Să definim o procedură mai generală pentru calcularea unui trinom de forma a2*x**2+a1*x+a0, care vă permite să specificați valorile ambelor x și a0, a1, a2. Să-i spunem PXA:

: PXA C E4 E3 * + * + ;

Când utilizați PXA, valorile a0, a1, a2, x trebuie să fie în secvența necesară pe stivă. De exemplu: a0=1, a1=2, a2=-3, x=4

* 1 2 -3 4 PXA . D -39

Corpul unei proceduri, împreună cu operațiile de bază ale procesorului, pot conține proceduri definite de utilizator. De exemplu, puteți defini o procedură P care, pe lângă calculele efectuate de PXA, va imprima o copie a rezultatului pe terminal și va elimina rezultatul din stivă.

:PXA. D;

În special, corpul unei proceduri poate include numele procedurii care este definită în sine, adică procedura poate fi recursivă. De exemplu:

: TIME [t] 1- TIME ;

Această procedură scade valoarea vârfului stivei cu 1 și se referă din nou la sine, adică funcționează ca un numărător de timp.

Contorul TIME, în principiu, nu se poate opri: procedura de scădere a unuia va fi efectuată iar și iar în timp ce procesorul funcționează. Dar în DSSP există instrumente care vă permit să controlați progresul procesului în funcție de rezultatele obținute - operația de control al progresului programului.

Execuție și repetare condiționată

Un program care este o secvență de comenzi executate în ordinea în care apar una după alta în notația sa se numește liniar. Pentru a face programul ușor vizibil (lizibil) și ușor de înțeles, acesta este împărțit în părți numite care au o anumită semnificație - proceduri, fiecare definită de propria sa secvență de proceduri, care la rândul lor sunt definite de secvențe de proceduri mai mici etc. la proceduri determinate direct de secvențe de comenzi DSSP. Un astfel de program, scris ca o ierarhie a definițiilor procedurilor, se numește structurat. Metoda de construire a unui program structurat, care constă în descompunerea treptată a problemei de rezolvat în subsarcini din ce în ce mai mici, se numește programare structurată.

Crearea nu numai liniare, ci și a oricăror programe folosind metoda de programare structurată este posibilă dacă există operații de executare a unei proceduri conform unei condiții, repetare a unei proceduri și ieșire dintr-o procedură repetată. Setul de comenzi de acest fel disponibil în DSSP oferă posibilitatea construirii structurate a unui program arbitrar.

Condițiile de executare sau neexecuție a unei proceduri sunt formulate relativ la semnul numărului, mai precis, relativ la semnul valorii pe care o are în prezent vârful stivei. Comanda principală de execuție a procedurii condiționate - BRS (BRanch on Sign) indică executarea uneia dintre cele trei proceduri numite după BRS, în funcție de semnul valorii curente a vârfului stivei. La executarea BRS, procesorul scoate elementul de sus din stivă, îi testează valoarea, iar dacă este negativ, atunci efectuează prima dintre aceste proceduri, dacă este zero, apoi a doua, iar dacă este pozitivă, atunci al treilea. Deci echipa

va face ca un element să fie eliminat din stivă și procedura N să fie executată dacă valoarea eliminată este negativă, procedura P să fie executată dacă este pozitivă și procedura Z să fie executată dacă este zero.

Un exemplu de utilizare a comenzii BRS este următoarea definiție a procedurii SGN

: SGN [X] BRS -1 0 1 ;

Această procedură înlocuiește valoarea X din partea de sus a stivei cu numărul -1 dacă X<0, числом 0, если X=0, и числом 1, если X>0. Procedura SGN este disponibilă în DSSP ca operație de bază a procesorului.

Comanda BRS, împreună cu selectarea unei proceduri din trei date, oferă capacitatea de a implementa instrucțiuni cu două valori de forma IF-THEN și IF-THEN-ELSE. De exemplu, propoziţia dacă x>0 atunci P1 altfel P0 corespunde comenzii BRS P0 P0 P1, iar propoziţia dacă x<>0 apoi P - comanda BRS P NOP P, în care NOP este numele unei operații goale. Dar în DSSP există o implementare mai eficientă a condițiilor cu două valori - comenzile IF-, IF0, IF+, BR-, BR0, BR+.

Comenzile grupului IF corespund instrucțiunii IF-THEN. De exemplu, comanda IF-P indică eliminarea elementului de sus din stivă și testarea semnului acestuia, iar dacă acest element are semnul minus, atunci executați procedura P. Comenzile IF0 P și IF+ P ordonă executarea procedurii P, respectiv , în cazul în care elementul eliminat este egal cu zero, iar în cazul în care valoarea acestuia este pozitivă.

Ca exemplu care ilustrează utilizarea comenzilor de grup IF, oferim definiția unei comenzi în limbajul de bază ABS care calculează modulul vârfului stivei.

: ABS [X] C IF-NEG [|X|] ;

Comenzile BR-, BR0 și BR+ corespund instrucțiunii IF-THEN-ELSE, care indică selectarea uneia dintre cele două proceduri numite după ele. Dacă semnul unui element scos din stivă coincide cu cel din desemnarea comenzii, atunci procedura numită prima este executată, iar dacă nu se potrivește, atunci se execută a doua procedură. De exemplu, comanda BR0 P0 P1 indică executarea procedurii P0 în cazul în care elementul scos din stivă este egal cu zero, iar dacă această condiție nu este îndeplinită, atunci executați procedura P1.

Comenzile luate în considerare vă permit să programați economic execuția unei proceduri în funcție de aceste condiții. Cele mai frecvente condiții de forma x<0, x=0, x>0 sunt implementate direct de instrucțiunile grupului IF. Conditii x<=0, x<>0, x>=0 sunt programate folosind instrucțiunile BR-, BR0, BR+ utilizând operația NOP goală ca primă procedură. De exemplu, clauza if x<=0 then P соответствует команда BR+ NOP P. Примером использования команд группы BR может служить следующая реализация команды базового языка NOT, заменяющей нулевое значение вершины стека единицей, а ненулевое - нулем.

: NU [x] BR0 1 0 ;

Ramificarea programului se face adesea după comenzi de comparare (<, =, >), producând o valoare logică de 1 sau 0 în funcție de rezultatul comparării a două numere. Comanda limbajului de bază MAX, de exemplu, poate fi programată după cum urmează:

: MAX C2 C2< IF+ E2 D ;

Grupul de comenzi de ramificare include și comanda de selecție BR, scrisă sub forma:

BR A1 P1 A2 P2 ... AK PK ... AN PN ELSE P0

La implementarea acestei instrucțiuni, procesorul execută mai întâi procedura pointer A1 și compară valoarea pe care a introdus-o pe stivă cu valoarea de sub ea din partea superioară anterioară a stivei. Dacă valorile se potrivesc, atunci primele două elemente sunt eliminate din stivă și se execută procedura P1 asociată cu pointerul A1, după care se face trecerea la instrucțiunea care urmează instrucțiunii BR (adică, în notația de mai sus, unul după cuvântul P0 din textul programului). Dacă valorile comparate nu se potrivesc, atunci elementul de sus este eliminat din stivă (adică rezultatul lui A1) și aceleași acțiuni sunt efectuate cu perechea A2 P2, atunci, dacă nu există potrivire, atunci cu perechea A3 P3 etc. până la AN PN inclusiv. Dacă niciuna dintre încercări nu a dat rezultate, se execută procedura P0 numită după cuvântul ELSE. De obicei, procedurile pointerului sunt constante numerice, de exemplu:

[x] C BR 5 NEG -3 ABS 0 NU ALTE T0 [y]

Ca urmare a executării acestei linii, valoarea y=-5 va fi obținută în vârful stivei dacă x=5; y=3 dacă x=-3; y=1 dacă x=0 și y=0 în toate celelalte cazuri.

În general, o procedură pointer poate fi nu numai o constantă numerică, ci și o variabilă sau orice altă procedură care satisface cerința simplă ca să nu scoată nimic din stivă și să împingă o valoare pe stivă.

Pentru a ilustra modul în care sunt utilizate operațiile de execuție a procedurilor condiționate, să modificăm procedura TIME din secțiunea anterioară, astfel încât contorul să se oprească atunci când apare o anumită condiție:

: TIME [t] 1- C IF+ TIME ;

Acum această procedură TIME se numește singură numai atunci când partea de sus a stivei este pozitivă. Contorul va funcționa exact de N ori dacă la începutul primei execuții a TIME vârful conține un număr pozitiv N. De exemplu, pentru a obține 7 operații, trebuie să setați

7 TIMP<ВК>

Deoarece IF+ în definiția TIME, ca orice operație condiționată, elimină elementul testat din stivă, iar acest element este necesar pentru operațiunile ulterioare, trebuie duplicat prin plasarea operației C (Copiere) înaintea IF+.

Recursiunea nu este mijlocul principal de executare a unei proceduri de mai multe ori. Pentru a programa cicluri în limbajul PARA există comenzile RP (Repeat - repeat) și DO (Do - do, execute).

Comanda RP W vă instruiește să efectuați procedura W din nou și din nou de un număr nelimitat de ori. Pentru ca repetițiile să se oprească, corpul procedurii W trebuie să conțină o operație EX (Exit) care este executată într-o anumită condiție. Operația EX trece la execuția unei proceduri care urmează în textul programului procedura repetată care conține această operație EX. Astfel, contorul implementat mai sus ca procedura recursivă TIME poate fi programat să repete procedura W, care este definită după cum urmează:

: W [t] 1-CIF0EX;

Pentru ca contorul să funcționeze de 25 de ori, trebuie să executați linia

Alături de operația EX, care este folosită în comenzile de execuție condiționată, există operațiuni de ieșire condiționată EX-, EX0, EX+, care produc același efect ca și comenzile IF-EX, IF0 EX, IF+ EX, adică consumând elementul superior , testându-și semnul și ieșind dacă semnul se potrivește cu cel specificat în desemnarea operațiunii. Operațiile EX, EX-, EX0, EX+ pot fi folosite nu neapărat în corpul procedurii repetate în sine (în cazul nostru W), dar și în procedurile la care se referă.

Ca exemplu, luați în considerare problema găsirii celui mai mare divizor comun a două numere naturale folosind metoda Euclidului. Esența metodei este că trebuie să scazi un număr mai mic dintr-un număr mai mare până când numerele devin egale între ele. Odată ce egalitatea este atinsă, se va găsi cel mai mare divizor comun.

Programarea se va realiza folosind metoda de dezvoltare de sus în jos. În primul rând, definim o procedură GCD care surprinde schema generală a algoritmului. Parametrii acestei proceduri sunt două numere M și N de pe stivă, pentru care se găsește cel mai mare divizor comun. Corpul procedurii GCD trebuie să specifice un proces ciclic pentru conversia valorilor pe stivă. Ca rezultat al acestui proces, două numere egale ar trebui să rămână pe stivă - oricare dintre ele poate fi luat drept cel mai mare divizor comun. Ținând cont de aceste considerații, procedura GCD poate fi definită după cum urmează.

: GCD RP PAS [din cap(M,N),din cap(M,N)] D [din cap(M,N)] ;

Acum este necesar să programați un pas al procesului iterativ, adică. definiți procedura STEP. Parametrii acestuia sunt două numere de pe stivă. Trebuie să comparați aceste numere și să părăsiți bucla dacă sunt egale, în caz contrar, scădeți cel mai mic din cel mai mare. Acest lucru se poate face, de exemplu, astfel:

: PAS C2 C2 - BRS NOP EX E2 C2 - ;

Acum nu mai există proceduri nedefinite în program și puteți începe să le verificați. Verificarea trebuie efectuată de jos în sus, adică mai întâi trebuie să vă asigurați că procedura STEP funcționează corect și numai apoi - GCD.

O operație DO în limbajul de bază face ca procedura numită după ea să fie repetată de N ori, unde N este numărul conținut în partea de sus a stivei în momentul în care DO este executat. De exemplu, pentru ca procedura P să fie executată de 8 ori, trebuie să setați

8 DO P

Dacă există cel puțin o operație de ieșire în corpul procedurii P și condiția de execuție a acesteia este îndeplinită înainte de a avea loc numărul specificat de repetări, atunci repetările vor fi încheiate prin părăsirea procedurii în același mod ca și în cazul operațiunea RP. De exemplu, când DO repetă procedura W de mai sus a cărei definiție conține IF0 EX, scrierea [T] 30 DO W va provoca 30 de repetări ale lui W dacă valoarea lui T>=30. Daca 0

Dacă până la executarea operației DO există o valoare zero sau negativă în partea de sus a stivei, atunci procedura care urmează DO nu va fi executată nici măcar o dată.

Pentru a ilustra utilizarea operației DO, definim o procedură NUM care numără numărul de biți non-zero din cuvântul de 32 de biți x dat în partea de sus a stivei.

Vom plasa contorul pentru numărul de unități la subvertexul stivei. Numărarea unităților va consta în repetarea procedurii NUMI de 32 de ori, în care vom examina un bit al cuvântului x. La ieșirea din buclă, numărul necesar ar trebui să fie în partea de sus a stivei.

: NUM [x] 0 E2 32 DO NUMI D [N] ;

Pentru a număra biții non-zero, folosim faptul că unul din cel mai semnificativ (al 31-lea) bit al unui cuvânt servește ca semn al unui număr negativ. Dacă cuvântul studiat este negativ, atunci trebuie adăugat unul la N. La sfârșitul procedurii NUMI, trebuie să mutați cuvântul studiat cu un bit spre stânga.

: NUMI C IF- N+ SHL ;

Implementarea procedurii N+ este destul de simplă: trebuie să adăugați unul în partea de sus a stivei fără a schimba partea de sus.

: N+ E2 1+ E2;

Procedurile repetabile pot conține operații RP și DO în corpurile lor, ceea ce duce la bucle imbricate și este permisă orice adâncime de imbricare. În acest caz, există o operație EXT pentru a ieși din bucla imbricată, indicând adâncimea imbricației în partea de sus a stivei. De exemplu, ieșirea din două bucle imbricate poate fi specificată astfel:

Trebuie avut în vedere faptul că utilizarea comenzii EXT necesită o atenție sporită, deoarece la modificarea programului, adâncimea de imbricare a buclelor se poate modifica și constanta corespunzătoare înainte de EXT va trebui modificată.

Date denumite

Stiva de operanzi este principalul, dar nu singurul mecanism de manipulare a datelor din DSSP. De asemenea, este posibil, împreună cu definițiile procedurilor, să se declare elemente și colecții standard organizate de elemente (așa-numitele structuri) de date, care sunt apoi disponibile pentru utilizare după numele lor. Prin implementarea declarațiilor de date, procesorul își rezervă memoria necesară stocării acestora și asigură mecanismele necesare pentru accesarea acestei memorie.

Limbajul de bază DSSP include un număr de cuvinte directive discutate mai jos pentru declararea variabilelor și matricelor. Pentru a extinde limbajul sistemului, în el pot fi introduse alte cuvinte de acest fel și, în consecință, alte elemente și structuri de date.

Cuvântul VAR declară o variabilă numerică de 16 biți. De exemplu, înregistrați

declară o variabilă X, adică îi spune procesorului că numele X este numele unei variabile. Procesorul asociază cu acest nume o celulă de memorie de 16 biți în care va fi stocată valoarea acestei variabile. Comanda de atribuire a variabilei X la valoarea conținută în partea de sus a stivei de operanzi are forma

Prin executarea acestei comenzi, procesorul scoate elementul de sus din stivă și își scrie valoarea în celula alocată pentru variabila X.

O comandă constând doar dintr-un nume de variabilă, fără litera ! în fața acesteia, face ca valoarea acestei variabile să fie împinsă în stivă, iar împingerea se face prin copierea conținutului celulei de memorie corespunzătoare, adică valoarea lui variabila rămâne neschimbată. Astfel, orice apariție a unui nume de variabilă X într-un program, cu excepția cazului în care este precedată imediat de un cuvânt care specifică o acțiune diferită, va împinge valoarea curentă a acestei variabile în stivă, la fel cum numerele date direct (literale numerice) sunt împinse în stivă. .

Ca exemplu, oferim o altă versiune a procedurii GCD discutată mai sus în care sunt utilizate două variabile de lucru.

: NU! X! Y RP PASUL X [GCD] ;

: PASUL X Y = EX+ X Y BR+ X-Y Y-X ;

: X-Y X Y - ! X ;

: Y-X Y X - ! Y;

După cum puteți vedea, programul a devenit ceva mai lung, dar vizibilitatea sa a crescut.

Cuvântul VCTR declară o matrice unidimensională (vector) de celule de 16 biți, cu numărul celui mai înalt element al acestui tablou dat de valoarea vârfului. De exemplu, ca urmare a înregistrării

9 VCTR ROW, procesorul rezervă 10 cuvinte de memorie de 16 biți adresabile secvenţial, formând un vector ROW(0:9). Mai întâi, numărul 9 este împins pe stivă, apoi se execută procedura VCTR, folosind elementul superior al stivei pentru a determina lungimea vectorului RÂND care urmează să fie creat.

Împingerea valorii elementului j-al al vectorului ROW pe stivă, 0<=j<=9, задается командой

[j]RÂND

Folosind un număr de element din stivă ca parametru, numele vectorului ROW face ca acel număr să fie înlocuit cu valoarea elementului corespunzător. Dacă cuvântul este imediat înaintea numelui vectorului RÂND, atunci elementului acestui vector indicat de vârf i se atribuie valoarea subvertixului, iar adâncimea stivei este redusă cu 2. De exemplu, puteți reseta Al 5-lea element al vectorului RÂND ca acesta:

De asemenea, este posibil să se combine vectori constanți, de ex. vectori de numere de 16 biți, ale căror valori sunt determinate atunci când este declarat și nu se modifică ulterior. Astfel, un vector de constante de 16 biți VC de lungime L+1 este declarat folosind cuvântul CNST sub forma:

CNST VC k0 k1 ... kL ;

unde k0, k1, ... kL sunt comenzi care împing o valoare în stivă. Cel mai adesea acestea sunt doar literale numerice, dar pot exista și nume de variabile, proceduri, precum și comenzi formate din perechi de cuvinte, cum ar fi, de exemplu, comanda pentru trimiterea adresei variabilei „X” discutată mai jos. Accesarea elementelor unui vector constant se face în același mod ca și la componentele vectorilor obișnuiți.

O matrice multidimensională de cuvinte de 16 biți este declarată folosind cuvântul ARR, precedat de valorile maxime ale indexului pentru fiecare dimensiune și numărul de dimensiuni. De exemplu, matricea tridimensională TIR(0:8,0:2,0:24) este declarată astfel:

Numărul 3 imediat înainte de ARR indică dimensiunea matricei declarate.

Împingerea unui element de matrice pe stivă se realizează prin specificarea indexului acelui element urmat de numele matricei. De exemplu, comanda de a împinge elementul TIR(0,2,2) în stivă este exprimată ca

În consecință, atribuirea acestui element valorii curente a vârfului stivei este specificată de comandă

Toate exemplele luate în considerare au ilustrat crearea de structuri din cuvinte de 16 biți. Cu toate acestea, limbajul vă permite, de asemenea, să definiți structuri de cuvinte pe 32 de biți și de 8 biți. Pentru a face acest lucru, prefixul LONG sau BYTE este plasat înaintea cuvântului care definește structura, respectiv. De exemplu,

5 BYTE VCTR X - definirea unui vector X de 6 octeți;

BYTE CNST Y 65 66 67 ; - definirea constantei vectoriale Y cu 3 componente;

10 20 2 LONG ARR MTRX - definirea matricei cuvintelor lungi MTRX(0:10,0:20).

Citirea elementelor structurilor de cuvinte și octeți se realizează în același mod ca și în cazul structurilor de cuvinte pe 16 biți. Dacă lungimea elementului este mai mică de 32 de biți, valoarea care trebuie preluată este plasată în cuvântul sau octetul inferior din partea de sus a stivei, iar partea superioară a vârfului este setată la zero. Valoarea atribuită unui element al unei structuri de cuvânt sau octet este, de asemenea, cuvântul sau octetul scăzut al unui cuvânt lung de 32 de biți din stivă.

Deși formatul de cuvânt pe 16 biți este utilizat la definirea datelor în mod implicit, acesta are și notația WORD. Este recomandabil să folosiți acest prefix atunci când programul este intenționat să fie transferat pe alte mașini, unde este implementat și DSSP și implicit poate fi diferit.

Structurile de date pe octeți sunt cel mai adesea folosite pentru stocarea și procesarea informațiilor text. Acest lucru se explică prin faptul că un octet este alocat în memoria computerului pentru a codifica un caracter. Pentru a specifica codurile de caractere în limba RAYA există o construcție #l, unde l este orice caracter disponibil pe tastatura computerului. Procesorul DSSP percepe această construcție ca o comandă pentru a împinge codul literei l în stivă. De exemplu:

Această construcție efectuează aceleași acțiuni ca un literal numeric egal cu codul literei specificate, dar utilizarea sa este mai de preferat, deoarece, în primul rând, vă eliberează de nevoia de a vă aminti codurile și, în al doilea rând, face programele mai ușor de înțeles. În special, putem da următoarea definiție a vectorului constant Y:

BYTE CNST Y #A #B #C ;

Este adesea convenabil să folosiți o notație simbolică pentru o constantă numerică într-un program. Pentru a oferi această capacitate, există un calificator VALUE:

Această comandă scoate elementul de sus din stivă și formează un cuvânt cu numele imediat după VALOARE. Utilizarea acestui cuvânt este echivalentă cu utilizarea unei constante numerice. De exemplu:

Lucrul cu memoria prin adrese fizice

Instrumentele luate în considerare oferă capacitatea de a denumi date și de a manipula datele indiferent de sistemul de adrese al computerului. Dar limbajul de bază include și instrumente care vă permit să manipulați adresele elementelor de memorie. Adresa unei variabile sau a unui element de matrice X este împinsă în stivă cu comanda

În cazul unui element de matrice, această comandă este precedată de valoarea indicilor.

Comanda limbajului de bază @ înlocuiește adresa de sus a stivei a unui cuvânt de memorie lungă cu valoarea care conține acel cuvânt. De exemplu, valoarea variabilei Y poate fi împinsă în stivă executând următoarea linie:

Instrucțiunea @B înlocuiește adresa cu valoarea octetului corespunzător, setând octeții mari din partea de sus a stivei la zero, iar instrucțiunea @L înlocuiește adresa cu un cuvânt de 32 de biți.

Există, de asemenea, comenzi pentru scrierea valorilor în memorie. Instrucțiunea!T scrie valoarea de 16 biți a subtopului la adresa eliminată din partea de sus a stivei. Comanda!TB determină o scriere similară a octetului inferior al subvertixului către octetul adresat de vârf, iar!TL scrie cuvântul de 32 de biți al subvertixului în cuvântul adresat de vârf. De exemplu, puteți atribui valoarea 15 celui de-al cincilea element al vectorului octet BV(0:5) cu următoarele comenzi:

15 5" BV!TB

Necesitatea de a lucra cu memorie la adrese fizice apare de obicei atunci când se creează programe care depind de arhitectura unui anumit computer, de exemplu, când se creează drivere I/O.

Operații suplimentare pentru lucrul cu date și memorie

Pentru a obține o mai mare eficiență și compactitate a programelor, în limbajul PARA au fost introduse următoarele operații:

0 <имя переменной>- reseta variabila;

1 <имя переменной>- atribui o unitate unei variabile;

1- <имя переменной>- scade valoarea variabilei cu unu;

1+ <имя переменной>- creste cu unu valoarea variabilei;

!- <имя переменной>- scade valoarea varfului stivei din variabila;

!+ <имя переменной>- adăugați valoarea vârfului stivei la variabilă.

Fiecare dintre aceste operații este ușor de programat folosind comenzi variabile de citire și scriere. De exemplu,

0 X este echivalent cu 0 ! X

1+ X este echivalent cu X 1+ ! X

X este echivalent cu X E2 - ! X

Utilizarea acestor operațiuni crește eficiența și vizibilitatea programelor.

În practică, deseori doriți să atribuiți o singură valoare tuturor elementelor unui tablou. În acest scop, există o operațiune în limba PARADIS!!!<имя массива>. Efectul său este de a atribui valoarea vârfului stivei tuturor componentelor matricei specificate. Operațiune!!! aplicabil matricelor cu elemente de orice format.

Exemplu de utilizare:

Codul de spațiu este scris în toate componentele matricei de octeți BUF.

Este adesea necesar să obțineți informații dintr-un program despre structura de date din spatele unui nume. Există câteva comenzi SIZE pentru asta? - afișați formatul elementului de date: 1, 2 sau 4 octeți și DIM? - afișarea numărului de elemente de date din structură. De exemplu, dacă datele sunt declarate

3 4 2 ARR LUNG Z

apoi, atunci când le sunt aplicate, aceste comenzi vor da următorul rezultat (numere zecimale):

MĂRIMEA? DIMENSIUNEA X? DIMENSIUNEA Y? Z

DIM? X DIM? Y DIM? Z

Setul de comenzi al procesorului DSSP include, în plus, patru comenzi care vă permit să citiți și să scrieți biți individuali din celulele de memorie ale computerului. Acestea sunt comenzile @BI, !BI, !BI0, !BI1. Parametrii pentru fiecare dintre ei sunt adresa cuvântului de memorie de pe stivă și numărul biților din acest cuvânt (rețineți că biții sunt numerotați de la dreapta la stânga, începând de la zero). Comanda!BI presupune, de asemenea, că există o valoare de bit pe stivă care trebuie scrisă. Comanda @BI înlocuiește parametrii specificați cu valoarea bitului selectat (0 sau 1), comenzile!BI0 și!BI1 setează bitul selectat la 0 și, respectiv, 1, eliminându-și parametrii din stivă, iar!BI comanda setează bitul selectat la valoarea celui mai puțin semnificativ al celui de-al treilea element al stivei și elimină toți cei trei parametrii săi din stivă. De exemplu, dacă valoarea variabilei X este numărul binar 101101, atunci rezultatele operațiilor enumerate vor fi următoarele:

" X [add.X] 3 @BI - al treilea bit al lui X, 0 " X 3 !BI - X este 100101,

" X [add.X] 0 !BI0 - X este 100100,

" X [add.X] 1 !BI1 - X este egal cu 100110.

Limbajul PARA are, de asemenea, instrumente pentru lucrul cu șiruri de octeți localizate în memorie. Pentru a specifica un șir de octeți, doi parametri sunt împinși în stivă: adresa de început a șirului (adică adresa primului său octet) și lungimea șirului (numărul de octeți din acesta).

Comanda!!!MB este folosită pentru a atribui toți octeții unui șir o valoare (specificată pe stivă). Consumă trei parametri din stivă: , unde b este valoarea atribuită, a și l sunt adresa de pornire și, respectiv, lungimea șirului de octeți. De exemplu, trebuie să resetați elementele din tabloul de octeți al 3-lea la al 10-lea octet TXT(0:20). Pentru a face acest lucru, puteți executa următoarea linie:

0 3 "TXT 8!!!MB

ca urmare, opt elemente consecutive ale matricei specificate, începând cu al 3-lea, vor primi valoarea 0. O comandă similară!!!MW are scopul de a umple o secvență de cuvinte de 16 biți cu aceeași valoare (numărul de cuvinte este indicată în partea de sus a stivei), iar comanda !!M - pentru a umple o secvență de cuvinte lungi.

Comanda!SB efectuează un transfer de șir de octeți. Parametrii săi sunt: ​​, unde a1 și l sunt adresa de pornire și lungimea șirului redirecționat, a2 este adresa de pornire a șirului către care se efectuează redirecționarea. Ca urmare a executării comenzii!SB, un șir de octeți de lungime l va fi localizat în memorie de la adresa a2, care este o copie exactă a șirului situat la adresa a1 înainte de efectuarea transferului. Șirul sursă și șirul destinație se pot suprapune. De exemplu, doriți să mutați elementele matricei de octeți M(0:10) după cum urmează: M(10):=M(9), M(9):=M(8), ..., M(1):= M(0). Pentru a face acest lucru, puteți utiliza comanda !SB:

0 " M 10 C2 1+ !SB

Ca rezultat, un șir de 10 octeți va fi mutat cu un octet către adrese de memorie în creștere.

Comanda!SB este convenabilă pentru lucrul cu stive de caractere (rețineți că fiecare caracter este codificat cu un octet). Permite, de exemplu, să atribuiți valoarea unui șir literal specificat explicit unui tablou de octeți. Pentru a specifica un astfel de șir, utilizați un text literal, adică o succesiune de caractere cuprinse între ghilimele, de exemplu „TEXT LITERAL”. Acest construct, atunci când este întâlnit într-un program, face ca adresa de pornire și lungimea unui șir de octeți care conține text citat să fie împins în stivă. Acești parametri pot fi apoi utilizați de comanda!SB. De exemplu, fragmentul „TABLE” 0 „TN !SB va face ca literalul „TABLE” să fie redirecționat către matricea TN.

Comanda SRCHB caută un octet specificat într-un șir. Parametri: , unde b este octetul a cărui primă apariție trebuie găsită, a și respectiv n specifică adresa de început și lungimea șirului în care se efectuează căutarea. Dacă n>0, atunci căutarea se efectuează de la adresa a la adresa a+n-1 (în direcția de creștere a adreselor), dacă n<0, то поиск ведется с адреса a до адреса a+n+1 (в сторону убывания адресов). В результате выполнения этой команды в стеке оказывается значение d, равное смещению относительно адреса a до первого вхождения байта b. Если такое вхождение не обнаружено, то d=n. Примеры:

#T „TEXT” SRCHB

#A „TEXT” SRCHB

#E „TEXT” [#E,a,4] 1- + -4 [#E,a+3,-4] SRCHB [-2]

Încheind analiza noastră asupra instrumentelor de lucru cu date, să ne oprim asupra problemei legate de stocarea datelor în memoria externă a unui computer, de exemplu. pe discuri magnetice. Există o comandă SAVE în limbajul PARA<имя файла>, care indică salvarea unei copii a memoriei principale a sistemului pe disc împreună cu obiectele definite de utilizator. În acest caz, zonele de memorie alocate pentru date prin operațiunile VAR, VCTR, ARR nu sunt scoase pe disc. Ca urmare, la încărcarea unui sistem salvat de pe disc, valorile datelor specificate nu sunt definite (acestea trebuie determinate în timpul execuției programului). În cele mai multe cazuri, acest lucru este justificat, deoarece nu este nevoie să irosești memoria discului pentru a stoca variabile de lucru, buffer-uri etc. Cu toate acestea, există date ale căror valori trebuie determinate imediat după pornirea sistemului de pe disc. Un exemplu este o variabilă care stochează viteza schimbului de date cu un dispozitiv extern. Când treceți la un alt curs de schimb, este suficient să modificați valoarea acestei variabile fără a face nicio corecție în program.

O indicație pentru procesor că valorile elementelor unei structuri de date ar trebui să fie scoase pe disc folosind comanda SAVE este prefixul FIX plasat înaintea definiției structurii, de exemplu

FIX VAR SPEED 20 FIX BYTE VCTR TABL

Lucrul cu structuri de date definite în acest fel nu este diferit de lucrul cu structuri definite în mod obișnuit.

Comenzi de control al procesorului

Limbajul PARA are un grup mic de comenzi concepute pentru a controla procesorul DSSP, sau mai precis, emulatorul procesorului DSSP.

Comanda RESTART determină repornirea procesorului. În acest caz, stiva este șters și este afișat un mesaj

Versiunea DSSP XX.XX.XX

Disponibil XXXXXW

iar procesorul intră în modul standby pentru introducerea comenzii. Această comandă poate fi utilă la depanarea programelor. Se execută și atunci când apar situații de eroare: indexul depășește limitele matricei, memoria liberă este epuizată etc.

Comanda \G este folosită pentru a continua execuția programului după oprirea la un cuvânt nedefinit. Dacă, în timpul executării unei proceduri, procesorul întâlnește o referință la un cuvânt nedefinit, emite un mesaj:

opreste nu stiu<слово> .

unde punctul este promptul procesorului DSSP, semnalând că procesorul este într-o stare de oprire la un cuvânt nedefinit. În acest mod, puteți executa orice comenzi de procesor, la fel ca în modul normal, când asteriscul este promptul. Există două moduri de a ieși din acest mod - fie prin executarea comenzii \G (atunci procesorul va continua să execute procedura întreruptă, sărind cuvantul nedefinit), fie folosind comanda RESTART.

Comanda EXEC îi spune procesorului să execute o procedură a cărei adresă se află în partea de sus a stivei. Pentru a obține adresa unei proceduri, utilizați comanda „” (două apostrofe), urmată de numele procedurii. De exemplu, ca rezultat al executării comenzii

Adresa procedurii ABS va fi împinsă pe stivă. Aceste comenzi vă permit să treceți o procedură ca parametru unei alte proceduri.

Grupul de comenzi de control al procesorului include operația SAVE deja menționată<имя файла>, care indică salvarea unei copii a sistemului pe disc, precum și comenzile care determină sursa de intrare a informațiilor text furnizate la intrarea procesorului. Inițial, această sursă este tastatura afișajului.

Comanda LOAD<имя файла>comută intrarea în fișierul disc cu numele specificat. Comanda PF - vă indică să introduceți comenzi din buffer-ul editorului de text. Comanda TEXEC transmite un șir de text la intrarea procesorului, ai cărui parametri sunt specificați pe stivă. La executarea comenzilor conținute în sursele specificate, intrarea comută automat pe tastatura de afișare.

Dicţionar Control Commands

Fluxul de comenzi de intrare perceput de procesor poate conține, în special, comenzi pentru definirea procedurilor și a datelor, determinând compilarea într-o reprezentare internă și stocarea corpului procedurii sau alocarea de memorie pentru datele specificate, precum și introducerea numelui. a procedurii compilate sau a structurii de date în dicționarul DSSP.

Dicționarul stabilește o corespondență între nume externe (utilizate în textul programului) și adresele obiectelor corespunzătoare acestor nume în reprezentarea internă. Atunci când procesează o definiție de procedură sau descrierea unei date numite, procesorul extinde dicționarul, formând în acesta o nouă intrare de dicționar care conține numele (mai precis, primele 7 caractere ale numelui) și adresa corpului procedurii sau descriptor de date asociat cu acest nume.

La programarea de sus în jos, corpurile de procedură pot conține referințe la obiecte încă nedefinite. În acest caz, în dicționar se formează intrări (titluri) de dicționar, marcate cu semnul incertitudinii. Pentru a afișa toate numele nedefinite pe ecranul de afișare, utilizați comanda UNDEF.

În timpul extinderii dicționarului, este posibil să se formeze subdicționare - colecții denumite de intrări de dicționar. Un subdicționar combină de obicei proceduri și structuri de date legate de aceeași sarcină. Pentru a evita confuzia între numele subdicționarelor și alte obiecte de program, numele unui subdicționar trebuie să înceapă cu litera $. Accesul la subdicționare pentru extinderea sau utilizarea lor poate fi deschis și închis cu comenzi speciale, care includ următoarele (numele $v înseamnă orice subdicționar valid).

GROW $v - crește subdicționarul $v, adică, până când se indică altfel, introduceți numele tuturor procedurilor și datelor compilate în subdicționarul $v;

USE $v - deschis pentru utilizare (pentru a căuta nume în el) subdicționar $v;

SHUT $v - închide capacitatea de a folosi subdicționarul $v;

ONLY $v - pune la dispoziție numai subdicționarul $v;

ANULARE - anulați NUMAI ultimul.

Există și o comandă?$, care tipărește pe afișaj numele tuturor subdicționarelor și starea acestora - indiferent dacă subdicționarul este deschis sau închis pentru căutare. Subdicționarul al cărui nume este tipărit în partea de sus este întotdeauna extins.

Procedurile de bază DSSP constituie un subdicționar numit $PRIME, deschis pentru utilizare și extensie în mod implicit, adică dacă nu exista nicio comandă care să instruiască extinderea altui subdicționar.

Să folosim, de exemplu, operația?$ pentru a imprima următoarea stare a subdicționarelor.

$PRG este deschis

$PRIME este deschis

$EDIT este închis

$PRIME este deschis

SISTEMUL este închis

Aceasta înseamnă că în momentul de față subdicționarul $PRG este deschis pentru creștere și utilizare, $PRIME este doar pentru utilizare, iar $EDIT și SYSTEM nu sunt disponibile. Rețineți că un subdicționar poate consta din mai multe secțiuni cu aceleași nume.

Există comenzi pentru ștergerea din dicționar a unui anumit set de intrări din dicționar și, poate, a obiectelor interne asociate acestora. Astfel, comanda FORGET $v șterge toate numele introduse în dicționar (nu doar subdicționarul $v) de la ultima execuție a comenzii GROW $v, împreună cu obiectele desemnate prin aceste nume, și anulează creșterea $v. subdicționar. Comanda PROGRAM $v efectuează aceleași acțiuni ca și comenzile FORGET $v GROW $v executate secvențial. Prezența unei astfel de comenzi la începutul oricărui program duce la faptul că atunci când programul este recompilat, vechea sa copie va fi ștearsă și se va forma un subdicționar pentru a stoca obiectele noii copii a programului. De exemplu, efectuând operația FORGET $PRIME pe dicționarul a cărui stare a fost afișată mai sus, obținem o nouă stare:

$EDIT este închis

$PRIME este deschis

SISTEMUL este închis

În timpul executării comenzii FORGET sunt afișate numele secțiunilor de șterse.

Vă rugăm să rețineți că numele subdicționarului SISTEM nu începe cu litera $. Acest lucru este acceptabil, dar duce la faptul că aplicarea comenzilor FORGET și RPOGRAM la acest subdicționar nu provoacă nicio acțiune (subdicționarul SYSTEM pare să nu existe pentru ele).

Datorită faptului că într-un program gata făcut, pentru marea majoritate a procedurilor, accesul prin nume extern nu este necesar, este posibilă eliminarea numelor acestora din dicționar, păstrând în același timp obiectele interne asociate acestora. Comanda CLEAR $v elimină toate numele din toate secțiunile subdicționarului $v, cu excepția celor care au fost precedate în textul programului (când erau definite) de prefixul:: (două puncte). De exemplu, ca urmare a executării de către procesor a următorului fragment de program:

:: : X+ Y !+ X ;

ȘTERGE $EXAMEN În subdicționarul $EXAMEN, vor rămâne doar numele X și X+, intrarea din dicționar Y va fi eliminată (deși variabila corespunzătoare cuvântului Y în reprezentarea internă va rămâne).

Comenzi I/O

Principalul mijloc de interacțiune a utilizatorului cu DSSP este terminalul, care este de obicei un afișaj cu raze catodice cu o tastatură. Din terminal se realizează introducerea inițială, editarea și depanarea programelor, pregătirea datelor și managementul întregului sistem. Programele și datele, precum și DSSP-ul în sine, sunt salvate ca fișiere pe discuri și pot fi imprimate pe o imprimantă. Pentru a controla intrarea/ieșirea, setul de proceduri de bază DSSP conține instrumentele descrise mai jos.

Programarea funcționării terminalului este asigurată de comenzi pentru introducerea și ieșirea numerelor, caractere individuale și secvențe de caractere (șiruri), precum și unele comenzi suplimentare.

Comanda TIB (Terminal Input Byte) inițiază o buclă în așteptarea ca o tastă să fie apăsată pe tastatura terminalului. Când o tastă este apăsată, codul de 8 biți al caracterului corespunzător este împins în stivă ca octet cel mai puțin semnificativ din partea de sus, cei mai mari 3 octeți conținând zerouri. O copie a caracterului introdus în acest mod este afișată pe afișaj. Există, de asemenea, o comandă TRB (Terminal Read Byte), care diferă de TIB prin faptul că trimiterea codului literei introduse către stivă nu este însoțită de afișarea acestei litere pe afișaj.

Comanda TIN (Număr de intrare terminal) inițiază un ciclu de introducere a unui număr în stivă și afișare a unui număr tastat de la tastatură. Numărul pe care îl introduceți trebuie să fie o secvență de cifre care poate începe cu un semn minus și se poate termina cu . În funcție de modul de intrare/ieșire setat, numerele sunt percepute de procesor ca hexazecimale, zecimale, octale sau binare. Dacă un număr hexazecimal începe cu o cifră notă cu o literă, atunci cifra 0 este adăugată înaintea acestuia. , adică cu biți de tăiere situati în stânga celui mai semnificativ bit având o greutate de 2 la puterea de 31.

Fiecare comandă TIN introduce un număr. Dacă trebuie să introduceți o secvență de numere pe o singură linie, acestea trebuie separate prin apăsarea tastei , iar comanda TIN trebuie executată din nou pentru a introduce fiecare număr în program.

O secvență care conține n caractere tastate de la tastatură este introdusă în memoria computerului sub formă de n octeți, localizați la adrese crescătoare secvențial, începând cu adresa a, folosind comanda TIS (Terminal Input String), înaintea căreia adresa a și numărul de caractere n sunt împinse pe stivă. De exemplu, să fie declarat un vector de octeți X de lungime suficientă. Trebuie să introduceți 9 caractere, atribuindu-le valorile elementelor acestui vector, începând cu elementul zero:

În mod similar, folosind comanda TOS, este specificată ieșirea unei secvențe de n octeți-litri cu adresa de pornire a:

Ieșirea către terminal a elementelor de text incluse direct în program este asigurată de design

."<текст>"

De exemplu, pentru ca textul ENTER OPTION NUMBER să apară pe afișaj atunci când se execută un anumit fragment de program, fragmentul trebuie să conțină intrarea „ENTER OPTION NUMBER”.

Comanda TON (Terminal Output Number) afișează numărul luat din partea de sus a stivei, iar lungimea câmpului de ieșire trebuie specificată în partea de sus. Numărul de ieșire este aliniat la marginea dreaptă a câmpului, pozițiile libere din stânga sunt umplute cu spații, iar dacă lungimea numărului depășește lungimea specificată a câmpului, atunci decuparea are loc în stânga. În modul I/O zecimal, numerele negative încep cu semnul minus.

Comanda TOB (byte de ieșire terminal) tipărește caracterul al cărui cod este specificat de octetul inferior din partea superioară a stivei. Adâncimea stivei este redusă cu 1.

Există, de asemenea, comenzi care controlează direct cursorul de afișare:

CR - mergeți la începutul unei noi linii,

SP - spațiu, adică deplasarea cu o poziție la dreapta.

Comanda BELL provoacă un semnal sonor scurt ("clopot").

Uneori, atunci când comunicați cu un terminal, este necesar să verificați dacă o tastă a fost deja apăsată și dacă afișajul a procesat deja comanda anterioară de ieșire. Acest lucru se poate face cu comenzile TTI (Terminal Test Input) și TTO (Terminal Test Output), care lasă un 1 pe stivă dacă apare evenimentul specificat și 0 în caz contrar.

Comenzile de ieșire ale imprimantei sunt similare cu comenzile de ieșire ale terminalului și se bazează pe un mnemonic similar în care literele LP (Imprimantă de linie) fie au înlocuit TO, fie sunt adăugate ca caractere principale. De exemplu, LPCR - tranziție la începutul unei noi linii, LPSP - spațiu, LPN - ieșirea unui număr dintr-un subvertix în câmpul specificat de vârf, LPB - ieșirea unui caracter, LPS - ieșirea unui șir de caractere . Există, de asemenea, comanda [N] LPT, care mută capul de imprimare în poziția N a liniei de tipărit, și comanda LPFF, care alimentează o coală de hârtie. Pentru a imprima text explicit, este convenabil să folosiți un text literal și comanda LPS, de exemplu:

„TABELUL VALORILOR FUNCȚILOR” LPS

Gestionarea întreruperilor și excepțiilor

La programarea perifericelor, devine necesară gestionarea întreruperilor. În DSSP această procesare este programată după cum urmează. Programul conceput pentru a gestiona întreruperea este o procedură DSSP obișnuită, a cărei definiție este precedată de prefixul INT, de exemplu INT: A !1+ I ; Prefixul INT asigură că starea procesorului este salvată în timpul unei întreruperi și restabilită atunci când întreruperea este procesată.

Pentru a lega un program de procesare la o anumită întrerupere, utilizați comanda LINK:

<адрес вектора>LEGĂTURĂ<имя процедуры>atunci când este executat, un apel la procedura de gestionare a întreruperilor este înregistrat de-a lungul vectorului corespunzător. Comanda LINK poate efectua atât legarea statică a unei proceduri cu o întrerupere, care are loc în momentul compilării programului, cât și legarea dinamică, în timpul execuției programului.

O întrerupere a procesorului este o modalitate prin care sistemul poate fi notificat cu privire la un eveniment care a avut loc în lumea exterioară. Evenimentele care necesită procesare imediată pot apărea și în program. Se numesc situații excepționale. Exemple de astfel de situații: împărțirea la zero, eroare de comunicare cu dispozitivul, sfârșitul fișierului de intrare etc.

În DSSP, situațiile de excepție sunt înregistrate folosind întreruperi de comandă. O întrerupere de comandă este o operație numită de apelare a unei proceduri de răspuns și este declarată după cum urmează:

CAPCANĂ<имя вызова> <конечная реакция>

De exemplu:

CAPCANĂ S1 „Situația S1”.

În primul caz, reacția finală la întreruperea S este procedura X în al doilea, când apare întreruperea S1, pe terminal va fi afișat următorul mesaj: Situația S1;

Un program a cărui execuție poate provoca o întrerupere își poate seta propriul răspuns folosind comanda de interceptare. DSSP oferă două tipuri de interceptări: ON și EON. Comenzile de interceptare pot fi utilizate numai în cadrul procedurilor și au formatul:

PE<имя прерывания> <реакция>

EON<имя прерывания> <реакция>De exemplu:

: A ... ON S "Întrerupere S" ... ;

: A1 ... EON S1 ABC ... ;

ON și EON stabilesc diferite tipuri de reacții. Dacă o nouă reacție este specificată de comanda ON, atunci când apare o întrerupere, procedura de reacție este executată, după care programul întrerupt continuă să ruleze. Dacă o reacție este specificată de instrucțiunea EON, atunci mai întâi stiva de operanzi capătă adâncimea pe care o avea în momentul în care a fost executată instrucțiunea EON, apoi reacția este executată și, la finalizare, executarea procedurii în care EON instrucțiunea a fost folosită se oprește imediat.

Să ne uităm la exemple. Procedura M introduce litere de la tastatura terminalului și verifică dacă este un număr. Dacă caracterul introdus nu este o cifră, întreruperea ND este ridicată. TRAP ND "Nu este un număr." : M RP M1; : M1 TRB [B] C #0< C2 #9 >&0 IF+ ND [B] TOB ;

Reacția finală la o întrerupere ND este mesajul: Nu este un număr.

Dacă M este apelat din procedura P1, care are propriul răspuns la întreruperea ND: P1 ON ND PR1 M ; : PR1 [B] CR „Eroare”. D #0 [#0] ; apoi atunci când se introduce un caracter nedigital, întreruperea ND va fi procesată de programul de reacție PR1 de tip ON, ceea ce va face ca mesajul să fie emis pe o nouă linie: Eroare. Caracterul introdus va fi înlocuit cu caracterul 0, după care M va continua să funcționeze.

Dacă M este apelat din procedura P2: P2 EON ND PR2 M ; : PR2 CR "Eroare. Sfârșitul introducerii." ; apoi atunci când se introduce un caracter nedigital, întreruperea ND va fi procesată de programul de reacție EON de tip PR2, ceea ce va face ca mesajul să fie emis pe o nouă linie: Eroare. Sfârșitul intrării., după care P2 va ieși. Stiva de operanzi va fi goală.

Dacă este necesar, întreruperea poate fi ridicată din nou în programul de reacție, extinzându-l astfel la programele de nivel superior. În acest caz, fie programul specificat în comanda de interceptare din procedura anexată, fie reacția finală se va ocupa de întrerupere. De exemplu, dacă modificați PR2 după cum urmează: : PR2 CR "Eroare. Sfârșitul introducerii." N.D.; atunci mesajul afisat pe terminal va fi astfel: Eroare. Sfârșitul intrării. Nu un număr.

DSSP are mai multe întreruperi de comandă încorporate, răspunsul la care poate fi furnizat în programele utilizatorului.

Assalamu alaikum wa rohmatullahi wa barakatuhu!
„Araba este limba locuitorilor Paradisului!” (sens aproximativ)
Dragi frați, vă rog să clarificați întrebarea referitoare la acest hadith, este de încredere? În general, sunt aceste cuvinte cuvintele profetului Muhammad, alayhi salaam?
BarakAllahu fikum wa jazakumullahu khair!

Wa alaikum salaam wa rahmatullahi wa barakatuh!

At-Tabarani în al-Ausat, din cuvintele lui Abu Huraira, relatează:
„Trimisul lui Allah, Allah să-l binecuvânteze și să-i dea pace, a spus: „Sunt arab, Coranul este în arabă, iar limba locuințelor Paradisului va fi arabă.”

Șeicul al-Albani l-a adus la Silsila al-Da'ifa numărul 161, spunând:

„Acest hadith este fictiv (maudu’). În realitate, nu există un singur hadith de încredere care să explice ce limbă vor vorbi locuitorii Paradisului, așa că este necesar să taceți și să nu vă scufundați în conversații despre această problemă, lăsând cunoștințele despre aceasta în seama lui Allah Atotputernicul și să vă implicați numai în ce va duce la comiterea acelor acte care vor aduce beneficii pe lumea cealalta!
Sheikh-ul-Islam Ibn Taymiyya, Allah să aibă milă de el, a fost întrebat: „Ce limbă vor vorbi oamenii în Ziua Învierii? Se va adresa Allah Atotputernicul oamenilor în arabă? Și este adevărat că limba locuitorilor Iadului este persană, iar cea a locuitorilor Raiului este arabă?
La care el a răspuns: „Lăudat să fie Allah, Domnul lumilor! Nu se știe ce limbă vor vorbi oamenii în acea zi, la fel cum nu se știe ce limbă le va vorbi Domnul lor, mare și glorios. Nici Allah Atotputernicul, nici Trimisul Său, pacea și binecuvântările fie asupra lui, nu ne-au spus nimic despre aceasta și, de asemenea, nu este de încredere că limba locuitorilor Iadului va fi persană, iar limba locuitorilor Paradisului va fi arabă. Și nu știm că a existat vreo dezacord în această chestiune între Însoțitori, Allah să fie mulțumit de ei. Dimpotrivă, s-au abținut să facă asta pentru că a vorbi despre asta este inutil. Cu toate acestea, în rândul generațiilor următoare au apărut dezacorduri cu privire la această problemă. Unii au spus că vor comunica în arabă, alții au spus că acest lucru nu se aplică locuitorilor Iadului, deoarece vor răspunde în persană și aceasta este limba lor în Iad. Al treilea este că oamenii vor comunica în asirian, deoarece aceasta este limba lui Adam, din care au provenit toate celelalte limbi. În al patrulea rând - că acest lucru nu se aplică locuitorilor Paradisului, deoarece vor comunica în arabă. Cu toate acestea, niciunul dintre ei nu are nicio dovadă care să-și susțină cuvintele, fie din rațiune, fie din surse Sharia, dar acestea sunt doar declarații lipsite de orice dovadă. Allah Atotputernicul știe mai bine!” Vezi Majmu'ul Fatawa 4/299.

În școli, pentru a studia elementele de bază ale algoritmizării, așa-numitele. limbaj algoritmic școlar (limbaj algoritmic educațional), folosind cuvinte în rusă care sunt pe înțelesul școlarilor. Spre deosebire de majoritatea limbajelor de programare, un limbaj algoritmic nu este legat de arhitectura computerului și nu conține detalii legate de proiectarea mașinii.

Exemple

Algoritmul în limbaj algoritmic este în general scris sub forma:

alg numele algoritmului (argumente și rezultate) dat condiţiile de aplicabilitate a algoritmului necesar scopul algoritmului început descrierea cantităților intermediare | secvență de comenzi (corpul algoritmului) con

În înregistrarea algoritmului, cuvintele cheie erau de obicei subliniate sau îngroșate. Pentru a evidenția blocurile logice, s-au folosit indentări, iar cuvintele pereche de la începutul și sfârșitul blocului au fost conectate printr-o bară verticală.

Un exemplu de calcul al sumei pătratelor:

alg Suma patratelor ( arg intact n, res intact S) dat| n > 0 necesar| S = 1*1 + 2*2 + 3*3 + … + n*n început intact eu | intrare n; S:=0 | nc pentru i de la 1 la n | | S:= S + i * i | kts | concluzie„S =”, S con

Atelier electronic

Pentru a sprijini studiul teoretic al programării într-un limbaj algoritmic, specialiștii de la Facultatea de Mecanică și Matematică a Universității de Stat din Moscova au creat un editor-compilator în 1985 „Atelier electronic”(„E” - în onoarea lui Ershov), permițându-vă să introduceți, editați și executați programe într-un limbaj algoritmic.

În 1986, un set de lumi educaționale (interpreți) a fost lansat pentru „Atelierul electronic”: „Robot”, „Desenător”, „Cu două picioare”, „Vehicul de teren”, care vă permit să introduceți pur și simplu concepte ale algoritmului. „E-workshop” a fost implementat pe computere: Yamaha, Corvette, UKNC și s-a răspândit.

Acest limbaj de programare a fost rafinat în mod constant și o descriere a unei versiuni ulterioare a „atelierului electronic” a apărut într-un manual în 1990. Sistemul de programare KuMir („Learning Worlds Set”), care acceptă acest manual, a fost lansat de întreprinderea InfoMir în 1990. Limbajul acestui sistem este numit și „Idol”.

În 1995, „KuMir” a fost recomandat de Ministerul Educației al Federației Ruse ca principal material educațional pentru cursul „Fundamentele informaticii și informaticii” bazat pe manualul de A. G. Kushnirenko, G. V. Lebedev și R. A. Svoren. .

Critică

Cu toate acestea, trebuie remarcat faptul că limbajul algoritmic, în absența detaliilor care să-l conecteze direct cu arhitectura computerului, totuși, referindu-se la limbaje similare Algolo, îi învață implicit pe școlari să se bazeze pe arhitectura von Neumann a mașinilor. (Arhitectura von Neumann este o implementare practică a unei idei anterioare numită mașina Turing. În plus față de ideea lui Turing, există și alte idei. Cea mai populară dintre ele se numește calculul Lambda: Alonzo Church a lucrat la ea. O mașină Lisp este un arhitectură care se bazează pe calculul Lambda.)

Legături

  • A. P. Ershov. Limbajul algoritmic în cursul școlar privind fundamentele informaticii și tehnologiei computerelor. 05/07/1985
  • Forum despre limbaje de programare ruse și instrumente de dezvoltare

Fundația Wikimedia. 2010.

Vedeți ce este „limba algoritmică rusă” în alte dicționare:

    Limbajul algoritmic este un limbaj formal folosit pentru a scrie, implementa sau studia algoritmi. Fiecare limbaj de programare este un limbaj algoritmic, dar nu orice limbaj algoritmic este potrivit pentru utilizare ca limbaj... ... Wikipedia

    Acest termen are alte semnificații, vezi Dragon (sensuri). Un exemplu de diagramă bloc a unui algoritm în limbajul DRAGON diagrama dragonului DRAGON (Friendly Russian Algorithmic Language That Provides Visibility) vizual... ... Wikipedia

    Acest termen are alte semnificații, vezi Limbajul algoritmic. Limbajul algoritmic academic este un limbaj formal folosit pentru a scrie, implementa și studia algoritmi. Spre deosebire de majoritatea limbajelor de programare, nu este legat de... Wikipedia

    Limbajul algoritmic (de asemenea limba algoritmică rusă, RAYA) este un limbaj de programare folosit pentru scrierea și studierea algoritmilor. Când studiezi informatica în școli, așa-numitul algoritm este folosit pentru a studia elementele de bază ale algoritmizării. algoritmic școlar... ... Wikipedia

    Limbajul de programare educațional este un limbaj de programare conceput pentru a preda programarea specialiștilor. Un astfel de limbaj trebuie să îndeplinească cerința principală: simplitatea. Cu cât este mai simplu, cu atât mai repede îl va stăpâni un începător. Posibilitățile unui astfel de... ... Wikipedia

    Un exemplu de diagramă bloc a unui algoritm în limbajul DRAGON diagrama dragonului DRAGON (Friendly Russian Algorithmic Language That Provides Visibility) este un limbaj algoritmic vizual creat ca parte a programului spațial Buran. Dezvoltarea acestui limbaj... Wikipedia