Documente Academic
Documente Profesional
Documente Cultură
Programarea calculatoarelor [i
limbaje de programare orientate obiect
popavdan @ yahoo.com
versiunea revizuit\ `ntre 3 [i 25 februarie 2007
CAP. 1 CAP.3
Servere de reţea 35
C A P. 5
Cum putem simula pe FOR şi REPEAT 96 Tipuri şi tipizare; De la tipuri simple la tipuri
neobiectuală 98
Bibliografie 222
Acest volum `[i propune s\ fie o punte, o leg\tur\, `ntre cursurile introductive de
programare structurat\ sau de structuri de date [i cele de ingineria program\rii.
Conceput ini]ial ca un manual de programare `n Oberon, unul din limbajele `n care
paradigma program\rii orientate obiect se prezint\ extrem de accesibil\ doritorului s-o
cunoasc\, cursul a evoluat `n anii urm\tori public\rii sale de c\tre Editura EduSoft c\tre
un curs care abordeaz\ holistic limbajele de programare imperative [i obiectuale.
Mul]umesc pe aceast\ cale editorului pentru acceptul de a l\sa acest curs sub licen]a
liber\ OpenDoc [i de a permite republicarea lui electronic\.
Actualmente cursul `nglobeaz\ referin]e la mai multe limbaje (C, C++, Oberon, Pascal
[i ocazional unele limbaje func]ionale ca Lisp [i Haskell) [i exemple privind conceptele
program\rii structurate [i program\rii orientate obiect, concepte prezentate `ntr-un ghid
universal de studiere a limbajelor imperative [i obiectuale, inclus [i el `n volum (la
pagina 54).
Totul este ilustrat cu multe exemple, cod surs\ [i capturi de imagini care fac u[oar\ `n
]elegerea chiar [i `n lipsa unui computer de[i recomand cititorilor s\ foloseasc\ unul
pentru a rezolva temele propuse. Mediile de programare necesare, at=t Pow c=t [i mai
noul Dev C++ se pot desc\rca de pe Internet.
Dup\ citirea acestui curs ve]i putea aborda fie c\r]i de proiectare profesional\ a
software-ului sau de ingineria program\rii fie c\r]i profesionale de proiectare a jocurilor
(de ce nu!), fie manualele unor medii de programare (IDE-uri) puternice [i ale
limbajelor lor asociate deoarece cursul v\ ofer\ cuno[tin]ele care lipsesc `ntre nivelul
[colar ori liceal [i cel profesional.
Mediul de programare cu care am `nceput este Pow (c\uta]i cuvintele cheie: Pow,
Oberon, Download cu un motor de c\utare). Pow este un IDE simplu care poate fi
folosit cu C++, Oberon sau Java. Este ideal pentru a face tranzi]ia de la vechile medii
Acum doi ani c=nd, proasp\t revenit din mediul industrial `n cel universitar, aveam `n
fa]\ sarcina de a face un curs despre programarea [i utilizarea calculatoarelor la o sec
]ie tehnic\ a universit\]ii Bac\u aveam `n fa]\ o multipl\ provocare. Era nevoie de un
limbaj [i de un mediu de programare care s\ `ndeplineasc\ o sumedenie de criterii.
Iat\ criteriile care m-au f\cut s\ aleg ca `nlocuitor al Turbo Pascalului un alt dialect
inventat de acela[i celebru N.Wirth (autorul Pascal-ului), limbaj cunoscut sub numele
de Oberon. A[tept\rile mele [i ale studen]ilor mei la adresa unui limbaj didactic [i
profesional totodat\ erau:
Cartea se adreseaz\ `n primul r=nd cursan]ilor anului `nt=i de la Univ. Bac\u, care au
nevoie de manuale (inexistente `n limba rom=n\) sau de note de curs. Cartea
poate ]ine locul notelor de curs pentru primele 8-9-10 cursuri predate, dar nu din
tot semestrul. Participarea la cursurile 10 - 14 devine astfel obligatorie.
Nu `n ultimul r=nd, cartea `ncearc\ s\ spulbere c=teva mituri [i false concep]ii despre
programarea calculatoarelor. Ve]i afla din ea ce `i trebuie unui adev\rat programator,
dincolo de cunoa[terea unui limbaj de programare, ve]i afla c\ unele propriet\]i ale
programelor nu pot fi depistate de alte programe ([i volumul include o demonstra]ie
simpl\ legat\ de problema opririi), ve]i `n]elege din acest motiv c\ [i antiviru[ii vor fi
`ntotdeauna ineficien]i. Acest lucru este din nefericire demonstrat [i de laboratoarele
universit\]ii `n care am depistat pesonal de doi-trei ani de zile viru[i pe care nu-i
recunoa[te nici m\car RAV-ul achizi]ionat cu c=tva timp `n urm\ dar cu mare tam-tam
de c\tre Microsoft. O frumoas\ dar trist\ confirmare practic\ a teoriei !
Exist\ `n acest volum chiar [i c=teva vorbe despre Linux, o platform\ software care mi-
a fost de mare ajutor, at=t la scrierea de mici compilatoare cu Bison [i Flex (c=t [i la
corectura final\ a volumului, realizat\ pe Mandrake Linux 10 [i PCLinuxOS 9 folosind
Open Office 1.1. Extrem de u[or de utilizat acest Open Office 1.1 pentru Linux care,
permite s\ expor]i documentele `n format PDF la o simpl\ ap\sare pe un buton !
Dan Popa,
Bac\u, august 2005
Tr\im `ntr-o lume din ce `n ce mai gr\bit\, mai complex\, mai interesat\ de aspectele
economice. Aceasta deoarece aspectele economice `nseamn\ bun\stare [i oportunit\]i,
combinate cu responsabilitate [i obliga]ii. Este o lume care se mi[c\ din ce `n ce mai
repede, am trecut practic nu `n secolul ci `n mileniul vitezei. Peste tot se cere productivitate
din ce `n ce mai mare a muncii, r\spuns din ce `n ce mai rapid (practic oricine va trebui s\
poat\ servi un client p=n\ a doua zi cel mult), se cere o calificare din ce `n ce mai `nalt\, o
bun\ cunoa[tere de noi tehnologii (fie c\ e vorba de proiectarea fie c\ e vorba de utilizarea
sau `ntre]inerea lor). Vechile obiceiuri [i deprinderi nu ne mai sunt `ntotdeauna de ajutor. Se
`ntrevede o schimbare. Munca `ns\[i se mut\ lent de la sediile marilor corpora]iii spre
birouri, sec]ii [i ateliere descentralizate sau chiar spre domiciliile angaja]ilor. (Personal,
lucrez deja la domiciliu.) Specificul felurilor de munc\ se mut\ de la prelucrarea materiilor
prime [i materialelor la prelucrarea informa]iei. Deja munca uman\, grea sau u[oar\, dar
adesea lent\ [i costisitoare a `nceput s\ fie `nlocuit\ de robo]i [i automate, fie c\ e vorba de
asamblarea [i vopsirea automobilelor, de lipirea circuitelor electronice pe pl\ci, de socotelile
lunare ale contabililor sau de banala v=nzare a cafelei la col] de strad\.
Iar toate aceste aspecte ale realit\]ilor lumii de m=ine reclam\ apari]ia unor noi categorii de
Bibliografie
La elaborarea acestui curs s-au utilizat materiale `n format electronic, c\r]i [i articole. Cele
mai importante dintre ele sunt indicate `n continuare.
Materiale `n format electronic:
Modul de examinare
Cursul este prev\zut cu un colocviu `n sesiunea de la sf=r[itul semestrului, iar la sec]iile
care urmeaz\ partea a doua a acestui curs `n semestrul al doilea se va da un colocviu `n
sesiunea din finalul semestrului respectiv. Pentru a putea participa la colocvii sunt necesare:
- Participarea la cursuri sau ob]inerea suportului de curs. Formal prezen]a la curs
nu este obligatorie, dar `n lipsa unui curs publicat [i a unor manuale de Oberon `n
limba Rom=n\ va trebui s\ procura]i cursurile, fie particip=nd direct la ele, fie
copiindu-le. Dac\ unul din cursuri nu apare la bibliotec\ [i a]i lipsit va trebui s\-l
copia]i de la colegii care au fost prezen]i `n sal\ sau s\ utiliza]i cursul tip\rit, dac\ e.
Aten]ie: `n cazul `n care opta]i pentru neparticipare la orele de curs sarcina de a
studia teoria program\rii calculatoarelor [i de a avea competen]e similare sau mai
bune ca ale colegilor dumneavoastr\ care au fost prezen]i v\ revine numai
dumneavoastr\. Limbajele moderne, cum este C++ sunt dificil de `nv\]at numai din
manualele tehnice, f\r\ explica]iile unui profesor. Riscul de a nu termina anul
universitar din cauza cursului de programare devine `n acest caz un risc major.
- Participarea la lucr\rile de laborator. Spre deosebire de prezen]a la curs, prezen]a la
laborator este obligatorie. Absen]a de la 3 lucr\ri de laborator (adic\ peste 20%
din total) de-a lungul unui semestru poate atrage dup\ sine neprimirea la
examene sau colocvii. Studentul respectiv mai are doar [ansa de a fi restan]ier.
Uneori pute]i recupera laboratorul, `n accea[i s\pt\m=n\, cu alt\ grup\ sau cu alt\
semigrup\ care are ore cu acela[i cadru didactic. Asisten]ii no[tri vor comunica mai
exact aceste aspecte la ora de laborator.
Dup\ parcurgerea acestui subcapitol trebuie s\ fi]i capabili s\ realiza]i f\r\ ajutor
urm\toarele activit\]i, fie `n laborator, fie la calculatorul personal. Primele dintre ele servesc
ob]inerii de pe Internet [i instal\rii mediului de programare Pow [i compilatorului de Oberon.
Le ve]i avea de efectuat cel mult o singur\ dat\. Celelalte vizeaz\ abilitatea de a porni
mediul de programare, de a scrie un program format dintr-un singur text (`n Oberon un
asemenea text se nume[te modul [i este prefixat cu cuv=ntul cheie MODULE), de a
modifica programul, de a-l compila (`nseamn\ a-l traduce `n limbajul procesorului), de a-l
executa (pentru a vedea cum func]ioneaz\ [i dac\ func]ioneaz\ corect) [i de a-l salva
(copia) pe discheta cu lucr\ri de laborator. ~n primele ore de laborator, deci, activitatea va
consta `n a realiza lucr\rile propuse [i programele proprii, parcurg=nd urm\toarele etape:
- pornirea mediului de programare (Pow sau altul indicat)
- deschiderea unei ferestre pe ecran `n care ve]i scrie noul program (noul modul), sau
a mai multor ferestre `n cazul proiectelor mari (situa]ie c=nd va trebui sa folosi]i [i
editorul de proiect [i s\ salva]i fi[ierul proiectului – cu extensia .prj sau alta)
- compilarea (adic\ traducerea programului `n limbajul microprocesorului)
- link-editarea (construirea programului executabil – imagina]i-v\ ceva cam ca la jocul
de Lego – din modulele compilate de dumneavoastr\ [i din alte componente se
construie[te prin `mbinare rezultatul). Acest program numit “executabil” este cel
care poate fi executat, adic\ pus `n func]iune. El poate fi apoi oferit beneficiarilor
`mpreun\ cu bibliotecile (.dll) necesare.
- salvarea (`nregistrarea) lucr\rii de laborator pe dischet\ (sau USB stick).
Instalarea Pow-ului decurge exact ca a oric\rei aplica]ii uzuale, tot ce v\ r\m=ne de f\cut
este s\ ap\sa]i periodic pe butonul Next.
Folosirea mediului Pow `mpreun\ cu limbajul Java, perfect posibil\, nu constituie `ns\ un
scop al acestui curs, dar pute]i totu[i experimenta cu diverse versiuni de JDK pentru a
vedea care func]ioneaz\ corespunz\tor.
Simbolul, iconi]a, mediului Pow este un bec de culoare vernil. Dac\ simbolul nu figureaz\ pe
ecran, pute]i porni mediul de programare Pow din meniul Start -> Programms -> Pow(32bit)
-> Pow. Dac\ iconi]a exist\ pe ecran, da]i cu mouse-ul un clic dublu pe iconi]\. Alte medii de
programare au alte figurine asociate, `ntreba]i pe care trebuie s-o folosi]i.
Imediat dup\ pornire, un prim program simplu, cu numele hello.mod este afi[at `n fereastra
deschis\. Cursorul, cel care indic\ locul pe ecran unde pute]i scrie sau [terge are forma unei
linii verticale pulsatile [i `l vede]i `n figur\ pe ultimul r=nd.
Sfat dep\[it: Dac\ folosi]i un vechi PC cu procesor 386, 486 sau chiar Pentium 1, pe care
ruleaz\ versiunea Pow pe 16 bi]i (cea pe care o g\si]i pe Simtel Net) sub interfa]a grafic\
Windows 3.1 sau 3.11 atunci pute]i fi `n situa]ia de a porni interfa]a cu o comand\ dat\ la
prompterul DOS, C:@> Comanda este WIN urmat de ENTER. Iconi]a Pow-ului se afl\ `n
fereastra Pow a Program managerului. Actualmente foarte pu]ine firme mai folosesc
sisteme Pentium 1 [i Windows din seria 3.x.
program
Despre meniul File
A devenit deja o tradi]ie ca aplica]ile moderne s\ grupeze `n primul meniu,
meniul File, comenzile necesare pentru `nceperea, continuarea [i punerea
la p\strare – pentru o continuare viitoare - a unei lucr\ri. Dac\ `n locul
[oricelului (mouse) lucra]i cu tastatura – [i profesioni[tii a[a lucreaz\ ! - sau dac\ pur [i
simplul mouse-ul este uzat, incomod, defect ori lipse[te, accesa]i meniul File cu tastele ALT
[i F. ALT trebuie s\ fie ]inut\ ap\sat\ atunci c=nd ap\sa]i pe F. Sublinierea indic\ `n fiecare
meniu tasta care trebuie ap\sat\ `mpreun\ cu ALT pentru a-l deschide.
Despre meniul Compile
Mediile de programare ofer\ pe l`ng\ meniurile File [i Windows un al treilea
meniu, Compile `n care sunt grupate comenzi necesare traducerii textelor
(programelor) scrise de dumneavoastr\ `n limbajul procesorului. Nici
procesorul nici celelalte circuite ale computerului nu `n]eleg de fapt limbajul Oberon (sau un
alt limbaj de nivel `nalt) `n care se programeaz\. Se poate traduce text cu text, fereastr\ cu
fereastr\ (ceea ce face op]iunea Compile) sau tot proiectul (ori tot proiectul cu excep]ia fi-
[ierelor nemodificate [i deja compilate), ceea ce fac Make [i Build. Eventualele erori g\site
de compilator vor fi semnalate [i vor trebui corectate `nainte de a compila din nou modulul
sau proiectul. Numai ceea ce a fost compilat f\r\ erori poate trece `n faza de Linkeditare.
Make face automat [i linkeditarea, dac\ se poate. Comanda Link, utilizat\ pentru pornirea
procesului de linkeditare este ultima din meniul Compile.
Dac\ ve]i lucra ca programator ve]i folosi zilnic aceste comenzi, tast=nd dup\ caz: ALT-F9
sau F9. Linkeditarea este numit\ de unii autori “editare de leg\turi”, deoarece link se traduce
prin leg\tur\.
Compilare, linkeditare – diferenţa dintre ele
Este preferabil s\ `n]elege]i deosebirile dintre aceste faze. Compilarea se
face modul cu modul, iar linkeditarea stabile[te printre altele leg\turile dintre
module, pe baza cuvintelor marcate cu stelu]\ (a[a cum este ProgMain* `n
Oberopn) [i a numelor de module. Practic, un modul `n care un asemenea nume a fost scris
gre[it, altfel dec=t `n modulul cu care se leag\, poate fi compilat f\r\ erori dar numele nu va
fi g\sit la linkeditare. ~ncerca]i s\ compila]i programul de mai sus scriind `n loc de
«ProgMain» doar «RogMain» at=t la `nceputul c=t [i la sf=r[itul textului. Compilarea se va
termina cu mesajul de succes «Done», dar linkeditarea nu va fi posibil\.
Cuvinte cheie: arhitectura calculatoarelor, IBM PC, XT, AT, Apple, procesor, memorie,
magistrale, FSB, date, adrese, ISA, PCI, controler, cipset, bridge, server, biprocesor, procesoare
X86, hardware, software, sistem de operare, resurse, BIOS, driver, aplicaţii, mediu de
dezvoltare, editor, compilator, linkeditor.
Istoria a ceea ce numim azi calculatoare personale, PC-uri, `ncepe pu]in `naintea anilor ‘80.
De[i termenul PC (personal computer) era folosit deja, `n august 1981 firma IBM `l folose[te
pentru a eticheta propriul s\u model de calculator de mici dimensiuni, destinat a fi folosit de
c\tre o singur\ persoan\. Ulterior a fost urmat de modele numite XT (extended technology)
apoi de AT (Advanced Technology). Ambele denumiri [i standarde mai exist\ doar prin
succesori. (De exemplu noile surse de calculator se numesc ATX, de la AT eXtins. )
~n anii 1981-1987, computerele de acest tip au constituit un standard de facto, datorit\
politicii firmei IBM de a face publice specifica]iile tehnice. Astfel, o sumedenie de produc\tori
au `nceput s\ fabrice subansamble sau chiar computere `ntregi care respectau standardele
IBM. Aceast\ popularizare a afectat puternic cota de pia]\ a firmei Apple (adev\rata
inventatoare a calculatorului personal), f\c=nd-o s\ scad\, iar pia]a s\ fie dominat\ acum de
ceea ce numim calculatoare compatibile IBM-PC sau, mai pe scurt PC-uri.
Defini]ie: Un PC este o ma[in\ de calcul al c\rei model a fost, primul IBM PC.
PROCESOR
Magistrala ISA
MEMORIE
Magistrala ISA
ADAPTOR VIDEO
DE
DISCHETE
ALTE COMPONENTE
Schematic, un IBM-PC era compus din: memorie, procesor, magistral\ ISA, controlere
ale perifericelor, periferice. Perifericele uzuale erau: tastatur\, monitor (display), unit\]i
de dischete, apoi disc hard (primele PC-uri nu posedau a[a ceva). Prin intermediul
porturilor seriale [i porturilor paralele se puteau conecta alte periferice: imprimant\,modem,
mai t=rziu mouse etc.
ISA # Industry Standard Architecture. Ce putem spune despre aceast\ veche magistral\ ?
Magistrala
circuitele " FrontSide
cipsetului
MEMORIE
HDD / CD
C
P
I
Controllere discuri
hard ( ATA-IDE), .
SCSI, SATA etc
PCI to
ISA
BRidge
DISPLAY
DISPLAY
A
S
I
Controlere
periferice lente
TASTATURA
Alte
periferice
Unitate de dischete
Not\ la `ncheierea edi]iei: La ora actual\ schemele pl\cilor de baz\ s-au diversificat [i mai
mult. Magistralele ISA [i EISA ([i bine`n]eles vechiul VLB – Vesa Local Bus) au disp\rut
practic din PC-urile moderne sau, dac\ exist\, exist\ numai pentru a conecta anumite
periferice mo[tenite (legacy) cum este controllerul de tastatur\. Sloturi ISA, EISA [i VLB nu
mai sunt vizibile pe mainboard-urile moderne. Au ap\rut sloturi noi pentru altfel de extensii.
Cartela Video este montat\ de obicei `ntr-un slot special de mare vitez\ (AGP 4 x.. 8 x...).
Se folosesc `nc\ denumiri ca NorthBridge [i SouthBridge dar leg\tura `ntre aceste circuite
se face printr-o magistral\ mult mai rapid\ dec=t PCI. Exist\ deja de ani buni [i solu]ii
integrate, totul (incluz=nd NorthBridge [i SouthBridge) `ntr-un singur chip.
Voi comenta totu[i schema de mai `nainte pentru a se `n]elege `n ce direc]ie s-a `ndreaptat
evolu]ia calculatoarelor `n timp, sub presiunea tehnologiilor noi [i a cererilor utilizatorilor.
Nevoia de a folosi `nc\ unele din vechile cartele de extensie proiectate pentru Magistrala
ISA, obliga sistemele s\ aib\ [i o magistral\ ISA. Leg\tura `ntre magistrala PCI [i magistrala
ISA se face printr-un alt "bridge", a[anumitul "PCI to ISA bridge". Verifica]i dac\ o plac\ de
baz\ pentru un computer are [i conector(i) ISA. Au tradi]ional culoarea neagr\. ~n lipsa lor
nu pute]i folosi `ntr-un nou computer vechile pl\ci de sunet, modemuri [i alte pl\ci de
extensie destinate magistralei ISA. Decide]i ce e avantajos: s\ cump\ra]i o plac\ de baz\
care mai are m\car un conector ISA sau s\ cump\ra]i alt\ cartel\ de extensie (`n englez\
«ad on card»). Deja magistrala ISA a disp\rut din PC-urile noi [i n-o mai g\si]i dec=t pe
c=teva pl\ci de baz\ destinate upgrade-ului sau `n PC-urile second hand mai lente.
Unii autori de documenta]ii, desen=nd schema pl\cii de baz\ cu procesorul [i memoria sus
[i perifericele lente jos, numesc cele dou\ bridge-uri, «northbridge» [i «southbridge», ca [i
cum le-ar indica pozi]ia pe o hart\.
Magistrala SCSI este de fapt o conexiune destinat\ a func]iona ~NTRE ni[te computere [i
periferice. Unele sisteme o folosesc pentru a conecta la computer discurile hard interne sau
externe. Dac\ dori]i s\ conecta]i dou\ computere (de exemplu dou\ servere redundante) la
acelea[i discuri hard ele trebuie s\ posede magistrale SCSI.
Servere de re]ea:
Termenul ‘server’ descrie un calculator cu func]ii speciale dintr-o re]ea de calculatoare.
(Aten]ie: pentru programatori server este altceva, este un strat de software - grup de func]ii
sau proceduri care ofer\ servicii altor module ale aplica]iei). El distribuie din resursele sale
(periferice, informa]ie - mai rar procesor [i memorie) altor calculatoare din re]ea. ~n re]elele
mici orice calculator poate `ndeplini o asemenea func]ie. ~n re]elele mari, sunt folosite
calculatoare special proiectate, inclusiv modele cu mai multe procesoare. Cel mai simplu
este biprocesorul. Deosebirea fa]\ de PC-urile obi[nuite este c\ pe placa de circuite a
biprocesorului exist\ un soclu pentru al doilea procesor [i exist\ circuite care asigur\
accesul procesoarelor la memorie [i magistrale, inclusiv transferul semnalelor de
`ntrerupere, f\r\ conflicte. (Vom vedea c\ electronica lor pune la dispozi]ia sistemului de
operare de pe aceste calculatoare func]ii suplimentare [i nu orice sistem de operare [tie s\
le foloseasc\. - Din acest motiv unele versiuni de Windows nu folosesc al doilea procesor
dintr-un asemenea computer, `n timp ce LINUX-ul `l poate folosi.) Cipsetul (setul de circuite
SISTEMUL DE OPERARE
HARDWARE
Exemple de aplica]ii:
- Procesorul de texte
- Programul de calcul tabelar
- Browser-ul (navigatorul) internet
- Programul de grafic\ vectorial\
- Programul de arhivare sau compresie
- Mediul de programare (sau pe scurt IDE-ul)
- Aplica]iile multimedia, etc.
Mediile de dezvoltare sunt acele instrumente complexe pentru realizarea aplica]iilor. Ele
includ:
- un editor de text (pentru scris programele)
- un compilator (pentru traducerea programelor `n limbajul procesorului);
Re]ine]i: compilatorul este de fapt un translator din limbajul `n care scrie]i programme `n cel
al procesorului.
- un linkeditor (pe rom=ne[te: editor de leg\turi; combin\ codul rezultat `n urma traducerii cu
alte module de program [i ob]ine un PROGRAM EXECUTABIL, care poate fi rulat)
Programarea calculatoarelor este activitatea de a transpune o
problem\ din universul real `n universul calculatorului. Ea poate fi
abordat\ `n mai multe moduri iar diversele limbaje `ncurajeaz\ mai mult
sau mai pu]in o anumit\ abordare a program\rii:
1. Programarea imperativ\
X:#2; “ x ia valoarea 2”
Y:#3; "y ia valoarea 3"
Z:#X^Y; " z ia valoarea care rezult\ ca sum\ a lui x cu y "
write(Z); “ scrie valoarea variabilei Z”
X#2; “ X ia valoarea 2”
Y#3; "Y ia valoarea 3"
x#X^Y; " x ia valoarea care rezult\ ca sum\ a lui X cu Y "
printf(%d, x); “ scrie valoarea variabilei x, sub form\ de num\r zecimal ”
Programul este format din structuri (un fel de instruc]iuni complexe care con]in `n interiorul
lor alte instruc]iuni). Instruc]iunea GOTO nu se mai folose[te, nu exist\ sau nu se
`ncurajeaz\ folosirea ei. Fiecare structur\ (asemenea unei piese de LEGO) are un `nceput [i
un sf=r[it ([i numai unul din fiecare). Cea mai mare structur\ posibil\ este chiar programul.
Fiecare structur\ se comport\ ca o instruc]iune [i poate fi inclus\ ca atare `n alte structuri.
read(x);
if (x div 2) # 0 then write ( ’x este par’) else write( ’x este impar’);
2.Programarea func]ional\:
Observa]i nota]ia specific\ pentru opera]ii - cu operatorul scris primul - [i pentru func]ii -
prima parantez\ se pune `naintea numelui func]iei.
3.Programarea logic\:
Prolog-ul nu face parte dintre limbajele care vor fi studiate `n cadrul acestui curs. Re]ine]i
Programarea orientat\ obiect este una dintre cele mai moderne paradigme. Universul
modelat este reprezentat ca o colec]ie de OBIECTE. Un obiect este o entitate care con]ine
DATE [i METODE (metodele sunt `n general func]ii – ca `n matematic\ - dar dac\ ele nu
returneaz\ nimic se numesc proceduri). Datele descriu propriet\]i statice ale obiectului iar
metodele implementeaz\ comport\ri ale obiectului la ac]iunea altor entit\]i (uzual tot
obiecte) asupra lui. Interac]iunea a dou\ obicte se realizeaz\ astfel: Unul din obiecte
apeleaz\ o metod\ a celuilalt. Metoda respectiv\ preia informa]ii (parametrii transmi[i de
primul obiect) [i `i prelucreaz\ a[a cum “[tie” al doilea obiect. Rezultatul interac]iunii depinde
astfel de ambele obiecte. De exemplu `ntr-un joc video cu arte mar]iale `n care lovesc
adversarul meu care are 100 de puncte de via]\ cu lovitura mea de for]a a 70 de unit\]i, `i
apelez de fapt metoda (procedura/func]ia) lui numit\ «prime[te_lovitura» cu parametrul
meu, 70 de unit\]i. Iar fiecare adversar put=nd avea alt\ metod\ «prime[te_lovitura», va
putea reac]iona altfel la lovituri. Metoda lui va face calculele dup\ formulele specifice
acestuia sc\z=nd din energia sa num\rul de puncte al loviturii (eventual multiplicat sau
diminuat sau altfel transformat). Vom vedea c\ un asemenea comportament diferen]iat al
obiectelor se nume[te polimorfism.
Obiecte cu aceea[i structur\ (acelea[i metode [i doar diferite valori ale
datelor) formeaz\ o clas\. De exemplu cuburi care pot avea diferite
dimensiuni. Clasa de obiecte este un tip de date descris de utilizator,
compus din informa]ii plasate `n c=mpuri – cum ar fi dimensiunea [i din
metode – func]iile care implementeaz\ diverse comportamente ale obiectelor. ~n
program pot exista mai multe obiecte din aceea[i clas\. Ele se numesc instan]e ale
clasei. Pentru simplificare, se pot defini clase noi, asem\n\toare cu o clas\ deja existent\,
specific=nd doar deosebirile (ce date [i metode are noua clas\ `n plus). O asemenea clas\
Exemple de limbaje obiectuale: Borland PASCAL, Turbo PASCAL, C^^, C#, Oberon,
ITCL [i lista ar putea continua (a]i auzit cumva de Python [i Ruby ?).
Paragraful “Ghid pentru studierea unui limbaj de programare imperativ” este însoţit de propriul
său set de cuvinte cheie. Dacă aţi studiat un astfel de limbaj, probabil vă sunt cunoscute. Oricum,
citiţi totuşi paragraful, măcar pentru cazul când aţi fi în situaţia de a explica (cuiva) ceva din el.
Nivelul client
# apel de func]ie de
Nivelul server = procedur\ (sau de metod\ a unui
modulul importat sau obiect) de la client la server
inclus cu directiva #include
Un proiect trece prin patru etape care sunt apoi iterate cu ocazia lans\rii versiunilor
ulterioare ale aplica]iei. Etapele sunt:
– analiza,
– modelarea,
– implementarea, (urmate evident de...)
– depanare (sau service de soft).
Analiza : caut\ s\ se afle c=t mai multe lucruri despre problem\, despre universul de
modelat format din utilizatori, re]ea de calculatoare, problem\, documente [i prelucr\ri.
Testarea modulelelor de cod se poate face realiz=nd odat\ cu modulul cerut [i un modul
client specializat care `l apeleaz\, cu scopul de a-l testa, oferind func]iilor (sau
procedurilor) de acolo diverse informa]ii [i verific=nd rezultatele.
Lucrare practic\: Dac\ un modul de rezolvare a ecua]iilor de gradul `nt=i
a*x ^ b # 0 con]ine o func]ie care returneaz\ pe x, modulul de test va
`nmul]i pe x cu a, va aduna b [i va testa dac\ e egal cu zero, [i aceasta
pentru mai multe valori ale lui a [i b, fie dinainte programate, fie dintr-un
spa]iu dat, fie aleatoare. Exemplul este pur didactic. {ansa de a fi simultan gre[ite [i
modulul de testare [i cel proiectat iar cele dou\ gre[eli s\ se anuleze `ntotdeauna reciproc
este extrem de mic\. Practic dou\ gre[eli at=t de bine (a se citi «nefericit») coordonate nu
se `nt=lnesc `n realitate.
Realiza]i ca activitate practic\: implementarea celor dou\ module.
Aten]ie: Va trebui s\ `ncepe]i un nou proiect (New -> Project -> Oberon-2 ->
Use template “opal display”) [i s\ ave]i grij\ s\ include]i pe lista fi[ierelor
proiectului (Project -> Edit) ambele module, care trebuie s\ fie salvate `n
prealabil, de preferat `n acela[i dosar, cel al proiectului . Un modul nou se adaug\ la un
proiect aleg=nd fi[ierul .mod dorit [i ac]ion=nd asupra butonului “add” din fereastra
editorului de proiect.
Dac\ lucra]i la laborator cu mediul de programare Pow `n Oberon sau `n C++ ghida]i-v\
dup\ figura urm\toare. {i celelalte medii de programare, de exemplu Dev-C++-ul ofer\ un
gestionar pentru module , o fereastr\ unde vede]i modulele ca o list\ sau grupate ierarhic.
Analiz\ [i analist : Analistul este persoana din echipa de dezvoltatori despre care se spune
c\ «dac\ este dat\ afar\ pe u[\, `]i intr\ `napoi pe fereastr\». Acest lucru este justificat de
rezisten]a personalului de alte specialit\]i la `ncerc\rile de a face analiza unei activit\]i de
informatizat. Practic `n faza de analiz\ va trebui s\ aduna]i informa]ii despre tot procesul de
informatizat, de la specificul procesului [i fluxul de produc]ie p=n\ la formatul documentelor
la intrare [i ie[ire, regulile de calcul ale noilor valori numerice [i regulile de realizare a
documentelor finale. N-ar fi r\u s\ cere]i sau s\ realiza]i `mpreun\ cu beneficiarul m\car un
set de documente complet, a[a cum va trebui s\ le produc\ viitoarea aplica]ie. Ele vor servi
[i ca date de test pentru aplica]ia pe are o ve]i realiza. Analistul caut\ deci s\ culeag\
maximum de informa]ii despre domeniul `n care se va folosi aplica]ia [i problemele concrete
pe care le va rezolva aceasta. ~n aceast\ etap\ se adun\ specifica]iile de la beneficiar, se
pun la dosarul proiectului exemplare (copii) ale documentelor sau datelor primare (de
prelucrat) [i specifica]ii ale datelor finale (de ob]inut) plus diagrame ale fluxurilor de date. Un
exemplu de asemenea specifica]ii sunt formatele rapoartelor - dac\ aplica]ia produce a[a
ceva.
Accentul cade pe `n]elegerea specifica]iilor [i a universului problemei `n general. Aminti]i-v\
c\ nu-l pute]i `nv\]a pe calculator ceva ce nu [ti]i dumneavoastr\.
Modelul static: Separ\ aplica]ia `n unit\]i constitutive numite module [i stabile[te ordinea
(bazat\ pe rela]ii CLIENT-SERVER) dintre modulele care vor forma ierarhia modulelor. (A
nu se confunda cu ierarhia claselor de la paradigma program\rii orientate obiect din cursul
precedent. Acea ierarhie era bazat\ pe «derivare de clase», adic\ pe rela]ii `ntre clase de
obiecte ale c\ror instan]e (obiectele din clas\) sunt construite unele prin extinderea altora
(din clasa p\rinte). ~n implementarea fiec\rui nivel pot s\ existe una sau mai multe ierarhii
de clase, cu obiecte necesare pentru rezolvarea sarcinilor nivelului respetiv.)
Practic, modelul static permite separarea aplica]iei `n componente mai mici, fiecare
asemenea component\ va deveni un fi[ier cu cod surs\ scris de un programator. ~n aceast\
etap\ se stabile[te din c=te fi[iere surs\ se compune aplica]ia, ce fel de proceduri [i func]ii
(adic\ proceduri func]ionale) vor con]ine acestea. Se aleg numele modulelor. ~n general se
recomand\ ca un modul s\ cuprind\ proceduri [i func]ii similare ca utilitate, structur\, scop
sau mod de apel.
Observa]ie: Modelarea static\ are un anumit grad de arbitrarietate. Felul cum va grupa
procedurile `n module depinde de experien]a proiectantului.
Modelul dinamic: Descrie ordinea `n care programul principal al aplica]iei va pune `n func]
iune (va face apeluri de pe pozi]ia de client la) alte module ale aplica]iei.
Accentul cade pe ordinea `n timp a evenimentelor care determin\ trecerea aplica]iei dintr-o
stare `n alta. Succesiunea acestor apeluri f\cute de programul principal poate fi
reprezentat\ grafic, asem\n\tor cu o schem\ logic\ sau, pentru cunosc\tori, ca un automat
finit determinist. Exist\ [i autori care deseneaz\ diagrama modelului dinamic `ntr-un mod
asem\n\tor cu o schem\ logic\.
Defini]ie: Automatul finit determinist (AFD) este o ma[in\ imaginar\ care
posed\ o mul]ime finit\ de configura]ii numite st\ri [i trece (`ntr-un mod
determinist, binedefinit, dup\ reguli precis determinate), dintr-o stare `n
alta. Dac\ ajunge `ntr-o stare special\ numit\ stare final\, AFD-ul se opre-
[te. Pot exista mai multe st\ri finale. Exist\ o singur\ stare ini]ial\. AFD-ul este reprezentat
ca un graf orientat (cam ca planul unui ora[ format din pie]e [i str\zi cu sens unic), `n care
nodurile sunt st\rile. Nodul - stare ini]ial\ este marcat cu o s\geat\ care intr\ `n nod. Un nod
stare-final\ e desenat ca dou\ cercuri concentrice de raze apropiate. Pe fiecare arc este
marcat evenimentul sau comanda care determin\ parcurgerea arcului.
~ntrebare: Cum [i din ce model afl\m ce date trimite acest modul principal spre func]iile pe
care le apeleaz\ ? (Dac\ nu pute]i r\spunde la `ntrebare ar fi cazul s\ mai citi]i o dat\
ultimele paragrafe). G`ndi]i-v\ c\ este vorba de func]ii.
5. Se presupune c\ programul este mai important [i mai complex dec=t datele. Ceea
ce este fals. Structurarea datelor nu este vizibil\ `n etapa de proiectare, de[i este necesar\.
( Cum a]i implementa o informa]ie compus\, de tipul “tabl\ de [ah cu piese” ?). ~n practic\,
de multe ori, pentru o aplica]ie, datele sunt mai importante, mai complexe sub raportul
structur\rii dec=t programele. Da]i exemple de asemenea situa]ii din lumea jocurilor video .
Programatorii de aplica]ii din domeniul economic folosesc alt\ diagram\ pentru a reprezenta
structura unei aplica]ii. Observa]i c\ nu specific\m `n diagram\ tipul datelor prelucrate ci
doar direc]ia fluxurilor de date. Diagrama (o g\si]i `n paginile urm\toare) e suficient de
general\ `nc=t s-o pute]i folosi pentru aproape orice aplica]ie, particulariz=nd-o
corespunz\tor.
~n esen]\ o aplica]ie din domeniul economic, de exemplu una realizt\ folosind FoxPro sau
Visual Fox Pro ar putea avea urm\toarele componente:
– meniul principal al aplica]iei, (care `nlocuie[te meniul Fox Pro). Din acest meniu se
apeleaz\ diferite instruc]iuni, diferite proceduri (grupuri de instruc]iuni) sau diferite alte
programe
– pentru cre[terea productivit\]ii aceste programe pot fi produse `n serie cu ni[te softuri
numite generatoare: generator de ecrane sau formulare (eng; forms), generator de
rapoarte, generator de interog\ri, generator de etichete etc.
– unele module introduc date `n baza de date, le-am figurat `n st=nga
– unele module prelucreaz\ date din baza de date (de exemplu fac verificari suplimentare
de consistenta), sunt programme scrise la de m=n\; le-am desenat la mijloc
– ultimele module extrag date din baza de date pentru a oferi rezultate (rapoarte de obicei).
Uneori aceste module sunt activate din alte p\r]i dec=t meniul principal (de pe WEB).
Baza de date
~n fig.: o reprezentare a modelului unei aplica]ii, folosit\ de cei care lucreaz\ `n domeniul bazelor de date.
Interac]iunea om calculator [i nevoia de universalitate (s\ pot aborda `ntr-un limbaj orice
0. Cum arat\ cel mai simplu program. Dar unul complex va fi la fel?
1. Tipuri de date. Afla]i cum se numesc tipurile: `ntreg, real, logic, caracter, [ir de caractere.
Alte tipuri mai exist\ `n limbaj ?
2. Variabile, declara]ii de variabile. Exist\ ? Sunt cu ini]ializare sau f\r\ ?
3. Mecanisme pentru intrarea [i ie[irea datelor: Instruc]iuni de intrare ie[ire (cazul PASCAL-
ului), biblioteci de func]ii pentru intrare/ie[ire (cazul C-ului), sau module cu proceduri de
intrare/ie[ire (cazul Oberon-ului). Alte mecanisme [i structuri algebrice pentru opera]ii de I/O
exist\ ?
4. Mecanisme pentru schimbarea valorilor variabilelor: instruc]iunea de atribuire. Exist\ alte
mecanisme (ex: pattern matching).
5. Un mod de a descrie noile valori: sintaxa expresiilor, operatori, operanzi.
Se precizeaz\ aici operatorii asocia]i diverselor tipuri de date [i prioritatea operatorilor
(ordinea opera]iilor !). Expresii aritmetice [i logice. Alte mul]imi cu opera]iile lor. Exist\ nota]ii
pentru mai multe valori deodat\ (ex: expresii regulate folosite `n limbaje de scripting sau `n
TCL/TK [amd)
6. Decizia este modul `n care se ramific\ fluxul execu]iei programului. Instruc]iunea IF [i
altele similare ei (CASE). Exist\ un mod de a scrie expresii condi]ionale ? (`n C exist\ un
operator “semn de `ntrebare - dou\ puncte” ? Expresia (a>b) ? 1 : 2 este `n C egal\ cu
unu dac\ este mai mare ca b altfel este egal\ cu doi.)
7. Prelucrarea seturilor de date de lungime aprioric necunoscut\ necesit\ reluarea execu]iei
unui program. Programele care execut\ instruc]iuni `n secven]\ nu pot face a[a ceva.
(Demonstra]i! ) Exist\ `n orice limbaj imperativ instruc]iuni de ciclare cu test ini]ial sau/[i cu
test final. (~n Pascal: WHILE DO. REPEAT UNTIL ) Este suficient ca `n limbaj s\ existe doar
una, cealat\ poate fi simulat\. (Ar\ta]i cum!) Exist\ tehnici de prelucrare a datelor structurate
imbricat (cu structuri [i substructuri conforme unei gramatici )?
8. Pentru prelucrarea seturilor de date de lungime cunoscut\ exist\ structura repetitiv\ cu
num\r cunoscut de opera]ii. ~n multe limbaje se nume[te FOR.
9. Secven]a de instruc]iuni. Afla]i cum se scrie aceasta: `n PASCAL: BEGIN ...; ... END ; `n
14. Clase, obiecte, ierarhii de clase, mo[tenire [i polimorfism . No]iunea de instan]\ a unei
clase.
15. Felul de tipizare al limbajului, este un limbaj cu tipizare strict\ sau nu ? Este un limbaj cu
tipuri polimorfice sau nu ? Exist\ mecanisme de genul «template-urilor» din C^^? alte
metode de a prelucra unitar date de tipuri diferite exist\ ?
16. Moduri speciale de a face opera]ii cu obiecte. Exist\ posibilit\]i de redefinire a
operatorilor astfel `nc=t ace[tia s\ opereze cu obiecte ? Exist\ conversii implicite de la
obiecte la tipuri simple ? (C++ ofer\ r\spunsuri afirmative la aceste ultime dou\ `ntreb\ri ).
Cuvinte cheie: editor de text, procesor de text, bloc, compilare, analizor lexical, analiză lexicală,
identificatori, analizor sintactic, analiză sintactică, arbore sintactic, analizor semantic, analiză
semantică, domeniu semantic, arbore operatorial, notaţie poloneză postfixată, stivă, PUSH,
POP, CALL, generare de cod, optimizare de cod, tabela de simboluri, tratarea erorilor, limbaj
de asamblare, cod intermediar, cvadruple (quadruple), interpretor, maşină virtuală, Java,
portabilitate, cod obiect, calculul valorilor constantelor, factorizarea invarianţilor, cod echivalent,
linkeditare, modul obiect, program executabil, .exe, .obj, .sym, debugger, bugg, debugging,
breakpoint, evaluator de expresii, execuţie pas cu pas, Object Inspector
Mediile de programare cu care se lucreaz\ la laborator, fie ele produse al firmei Borland,
(Turbo Pascal, Turbo C, Borland C^^,etc.), fie medii freeware (Free Pascal, Pow –
Programmers Open Workbench, Dev C++) cuprind, cel pu]in urm\toarele componente,
despre care vom discuta `n continuare:
- editorul de text (cu facilit\]i de: operare cu blocuri, c\utare [i `nlocuire de texte, editare `n
ferestre multiple, salv\ri, copieri, [tergeri de blocuri de text)
- compilatorul limbajului
- alte componente
Defini]ie: Compilatorul este programul care traduce din limbajul de nivel `nalt (`n care
programa]i) `n limbaj ma[in\, adic\ `n limbajul procesorului (real sau virtual) sau `n alt limbaj
Mai interesant [i mai sofisticat din punct de vedere tehnic, dintre toate acestea trei, este
compilatorul. Cum este el alc\tuit nu se observ\ din func]ionarea sa. A[a c\ propunem s\
«ridic\m capota» care ascunde acest «motor» [i s\ descoperim componentele sale [i modul
cum realizeaz\ traducerea.
Uzual, c=nd se deseneaz\ schema bloc a unui compilator, programului principal nu `i este
reprezentat meniul. Alteori meniul nici nu exist\ compilatorul fiind un simplu program
executabil lansat dintr-o linie de comand\ cu parametri. Atunci c=nd compilatorul este inclus
`ntr-un mediu de programare, interfa]a acestuia preia rolul programului principal (mai exact
al nivelului client). Nu uita]i c\ de obicei compilatorul prime[te diverse op]iuni sub form\ de
linie de comand\ sau, la unele compilatoare, sub forma unor comentarii speciale incluse `n
programul de compilat. Unele medii de programare permit s\ stabili]i dumneavoastr\ cum
arat\ linia de comand\ dat\ pentru pornirea compilatorului (Eclipse, Emacs, Pow )
~n fig.: Schema unui compilator (programul de compilat intr\ prin st=nga figurii [i rezultatul iese prin dreapta)
~n realitate aceste faze nu sunt succesive ci mai cur=nd subordonate. Se poate desena [i `n
~n fig: Schema practic\ a unui compilator (programul de compilat intr\ prin st=nga figurii [i rezultatul iese prin dreapta
jos) – dup\ P.D.Terry – Compilers and Compilers Generators
Ultimele dou\ sunt la nevoie apelate de oricare din celelalte module componente. S\ le lu\m
`n discu]ie r=nd pe r=nd, pe toate:
Analizorul lexical: Prime[te la intrare programul surs\, care, pentru el, este un [ir de litere.
Exemplu:
PROGRAM Nume;
VAR x , y : INTEG ER;
BE G I N
EN D.
~ncadra]i `ntr-un p\tr\]el fiecare liter\ din textul de mai sus, pentru a v\ face o idee cum sose
[te textul, simbol cu simbol, la analizorul lexical.
El devine, dup\ analiza lexical\, o secven]\ de identificatori:
(Exemplul este pur didactic. Dac\ dori]i v\ pute]i imagina analizorul lexical ca un foarfece
care taie panglica textului limbajului `n buc\]i cuprinz=nd fiecare un cuv=nt [i clasific\ `n
categorii lexicale cuvintele ob]inute astfel. ~n consecin]\, identificatorii introdu[i de
programator sunt separa]i de cuvintele rezervate [i de operatorii scri[i cu mai multe litere,
cum este “mai mare sau egal” .)
VAR X , Y : INTEGER ;
BEGIN
END .
Analizorul sintactic este clientul analizorului lexical adic\ cel care are
nevoie de aceste cuvinte deoarece regulile gramaticii, pe care
analizorul sintactic le folose[te sunt reguli de succesiune a
cuvintelor, nu a literelor.
La fiecare apel, analizorul lexical cite[te din textul programului literele una c=te una p=n\
determin\ urm\torul atom lexical (adic\ un simbol simplu, unul compus - ca atribuirea - sau
un cuv=nt.) Pe acesta `l returneaz\ analizorului sintactic. La urm\torul apel citirile continu\
de unde s-au terminat citirile precedente. Exist\ [i implement\ri de compilatoare `n care
analizorul lexical este un modul separat.
Erori de sintaxa cum ar fi cele de mai jos sunt semnalate `n faza analizei sintactice.
Exemplul 1.
((3^5-))) este o expresie cu gre[eli de sintax\
Exemplul 2.
REPEAT
...
BEGIN
...
UNTIL
...
END
{tia]i c\ `n Pascal exist\ structuri ambigue din punct de vedere al analizei sintactice ?
Exemplu:
if <condi]ie1> then if < condi]ie2> then <instruc]iune1>
else <instruc]iune2>
~ntrebare: Cui apar]ine else <instruc]iune2>, primului sau celui de-al doilea if ? ~n Pascal
dezambiguizarea se face conform regulii:
“else apar]ine ultimului if .. then care nu are else.
~n Oberon if are forma IF ... THEN ... ELSE ... END , respectiv forma
IF ... THEN ... END ceea ce duce la distinc]ia `ntre:
IF ... THEN IF ... THEN ... END ... ELSE ... END [I
IF ... THEN IF ... THEN ... ELSE ... END ... END
Problema nu se mai pune `n Oberon. ~n primul caz ELSE apar]ine primului IF [i `n cel de-al
doilea caz urm\torului.
~n urma analizei sintactice rezult\ un arbore sintactic. Nodurile sale corespund cu regulile
din gramatic\. De exemplu instruc]iunea
WHILE (1 < P ) & ( P < 9) DO P:=P+Q;
produce un arbore cu alura celui din imagine (`n realitate va fi ceva mai `mpodobit cu
diverse valori auxiliare numite atribute).
~n fig: Arborele sintactic al instruc]iunii WHILE (1 < P ) & ( P < 9) DO P:=P+Q; – dup\ P.D.Terry – Compilers
and Compilers Generators
Exerci]ii:
1) Desena]i arborii operatoriali (aten]ie, operatorii sunt `n noduri) pentru:
IF ... THEN IF ... THEN ... ELSE ... END ... END
Indica]ie: Argumentele lui if…then…else sunt expresia boolean\ [i cele dou\ instru]iuni.
Dac\ vi se pare greu `ncepe]i cu a doua expresie, cea a sumei celor trei valori a,b,c.
2) Transcrie]i `n form\ polonez\ postfixat\ (adic\ operatorul este plasat
dup\ operanzi) expresia (a^b)^c . Verifica]i felul cum cum aceast\
transcriere, a b ^ c ^ permite calculul rezultatului cu ajutorul unei stive de
valori `n care valorile variabilelor se depun iar fiecare operator scoate
argumentele necesare, face calculul [i pune rezultatul la loc `n stiv\.
~ntrebare: Cum se poate calcula valoarea expresiei aritmetice c=nd se cunoa[te arborele ei
operatorial ? Indica]ie: Se poate defini o func]ie recursiv\ de evaluare a unui arbore, pe
ideea c\ arborele este format din operator [i ... al]i arbori care sunt operanzii.
~n urma analizei semantice rezult\ o valoare din domeniul semantic ( e vorba de o informa]ie
complex\, structurat\). Aceast\ informa]ie permite mai departe generarea de cod.
Generatorul de cod: Pe baza rezultatului analizei semantice el genereaz\ cod ma[in\ sau
program `n limbaj de asamblare, bytecode (cazul limbajului Java) sau alt fel de cod
intermediar. Practic aici se produce codul care este rezultatul compil\rii.
R\spuns posibil:
Optimizatorul de cod: Prelucreaz\ codul rezultat `n urma gener\rii pentru a ob]ine un cod
echivalent, mai compact sau/[i mai rapid. Optimizatorul se poate ocupa de:
-calculul expresiilor constante
-`nlocuirea unor grupuri de instruc]iuni din cod cu c=te-o instruc]iune echivalent\ grupului
respectiv
- factorizarea invarian]ilor din cicluri [i alte optimiz\ri
Exemplul 1:
X:=3^5^7
se poate compila gener=nd cod ca [i cum a]i fi programat X:#15
Exemplul 2:
for i : = 1 to 100 do begin
z:=x+12;(*calcul ce nu depinde de i *)
j:=j+i;
end;
Optimizatorul de cod depisteaz\ c\ atribuirea z:=x+12 se execut\ inutil de 100 de ori
(deoarece valoarea lui x nu se modific\ `n interiorul buclei) [i va scoate `nafara acesteia
atribuirea cu pricina, gener=nd un cod ca [i cum a]i fi scris programul:
z:=x+12;
for i : = 1 to 100 do begin
j:=j+i;
end;
Observa]ie: Codul generat `n urma optimiz\rii nu este totdeauna func]ional echivalent cu cel
scris de dumneavoastr\. De exemplu difer\ timpul `n care se execut\ el, ceea ce uneori
poate fi dezastruos. (Dac\ programatorul folose[te bucla ca pe o temporizare, codul
optimizat va face o pauz\ mai scurt\. A[a ceva este inadmisibil pentru anumite sisteme
informatice, de exemplu cele destinate a lucra `n tip real.)
Recomandare: Scrie]i dumneavoastr\ codul surs\ (programul surs\) astfel `nc=t s\ nu fie
nevoie de asemenea optimiz\ri. Prefera]i s\ face]i dumneavoastr\ optimiz\rile scriind din
start c=t mai bine, ba chiar optimal, programul ! ~n general un compilator m\re[te prin
optimizare viteza codului de 2-4 ori pe c=nd un programator care scrie cod corect [i folose
[te un algoritm mai bun poate ob]ine o vitez\ de peste 10 ori mai mare.
- link-editor (este cel care combin\ modulele de cod obiect rezultate din urma compil\rii
divereselor fi[iere surs\ ale unei aplica]ii `ntr-un singur program executabil.) Este cel care
produce fi[ierele .exe .
Practic: Dac\ `n Oberon scrie]i gre[it numele procedurii ProgMain dar consecvent, eroarea
nu va fi sesizat\ la compilare ci doar la link-editare, atunci c=nd link-editorul caut\ `n diferite
module obiect punctele de intrare ale procedurilor. (Tabelele de simboluri ale diverselor
module se folosesc `n acest scop.)
- debugger (depanator)
Denumirea vine de la “bugg” care are `n jargonul informatic sensul de “scam\”, “defect”.
Depanarea programelor se nume[te [i “debugging”. Istoric vorbind, “debugging” cu sensul
{tia]i c\: Exist\ limbaje a c\ror distan]\ fa]\ de limbajul ma[in\ este foarte mare iar
traducerea se face via o serie de mai multe limbaje intermediare ?
Se consider\ `n general, dup\ absolvirea liceului, c\ a cunoa[te unul, dou\ sau trei
limbaje de programare te face s\ fii programator. Din nefericire aceast\ opinie este
FALS|, falsitatea ei fiind recunoscut\ de patronii care au angajat ca programatori unii
studen]i. Limbajul de programare r\m=ne pe lista instrumentelor teoretice necesare dar
mai trebuie [i altceva. S\ facem deci lista (lista nu este exhaustiv\.):
Ingineria program\rii v\ ajut\, atunci c=nd proiecta]i o aplica]ie mare, s\ stabili]i din ce
componente este ea realizat\, cum se vor reflecta aceste componente `n fi[ierele
(modulele) proiectului. Pentru am\nunte revede]i paragrafele anterioare despre ingineria
program\rii structurate. Paradigma OOP beneficiaz\ [i ea de reguli de inginerie a
program\rii.
Tehnici de programare : V\ conduc spre a afla cum se vor implementa diversele servicii
ale aplica]iei sub form\ de proceduri. ~naintea acestei etape nu [ti]i de obicei CUM se
rezolv\ problema pe care trebuie s-o rezolve o procedur\, ci doar CE are ea de rezolvat.
Teoria const\ `ntr-o list\ de metode uzuale pentru abordarea problemelor noi, atunci c=nd
algoritmii lor de rezolvare nu sunt din start eviden]i. Exemplu: O tehnic\ de programare
comun\ este “Divide et impera” : O problem\ dat\ se rezolv\ imediat dac\ e foarte
simpl\ sau, dac\ este complex\ se `mparte `n dou\ (ori mai multe) probleme analoage dar
mai simple (d.p.d.v. al datelor). Pentru a le rezolva se apeleaz\ acela[i algoritm, el `mp\r]
ind iar problema rezultat\ `n probleme mai simple, [amd p=n\ le poate rezolva pe toate.
Trebuie s\ existe `n acest caz [i o modalitate de a construi solu]ia problemei mari din solu]
iile problemelor mici. Ilustrare: Algoritmul de sortare rapid\ Quicksort, se bazeaz\ pe
aceast\ idee, el caut\ (sau a[eaz\ prin c=teva permut\ri ) la mijlocul [irului un element
care este mai mare ca primele [i mai mic ca ultimele. Cele dou\ p\r]i ale [irului sunt
sortate mai departe tot cu Quicksort (recursiv). Cele mai simple [iruri sunt cele de un
element sau dou\, care nu se mai `mpart mai departe.
START
Algoritmul A
(decide dac\ programul dat se opre[te )
Nu
STOP
~n fig.: Schema logic\ a algoritmului A’,nou creat `n ipoteza eisten]ei lui A. Dreptunghiul exterior nu face parte din schem\.
Vom nota noul algoritm cu A’, [i vom vedea c\ existen]a lui produce o contradic]ie.
Limbajele de programare
Abordarea practic\ a unui limbaj nou poate `ncepe cu sintaxa celui mai simplu program
`n acel limbaj. El va fi minimal sub raportul faptului c\ eliminarea de cuvinte din el `l face s\
fie un program incomplet. Se pot da mai multe exemple precum [i programe pu]in mai
complicate, ilustr=nd introducerea unor noi instruc]iuni / declara]ii / concepte.
PROCEDURE ProgMain*;
BEGIN
END ProgMain;
END Identificator1.
Unde Identificator1 trebuie s\ coincid\ cu numele fi[ierului surs\ .Forma general\ a unui
modul este `ns\ alta:
BEGIN
Instruc]iuni de in]ializare (* care lipsesc la multe module *)
END Identificator1. (* Se termin\ cu punct.*)
Un modul poate con]ine mai multe proceduri (`n C vor fi func]ii), fiecare procedur\ cu proprii
s\i parametri, (se vor scrie `n parantez\) cu propriile variabile locale (se declar\ dup\ VAR),
cu propriile instruc]iuni: Instruc]iunile se scriu `ntre BEGIN-ul [i END-ul fiec\rei proceduri.
Unitatea component\ a modulului e procedura. Modulul poate avea propriile lui constante
(ar\ta]i unde!), tipuri noi definite [i variabile declarate dup\ VAR -ul de la `nceput, eventual
propria lui list\ de instruc]iuni de ini]ializare, `ntre BEGIN-ul [i END-ul de la sf=r[it.
Ca [i modulele, procedurile pot avea declarate, pentru uzul lor local, constante (`n Oberon
se scriu `ntr-o sec]iune care `ncepe cu CONST), tipuri (`ntr-o sec]iune care `ncepe cu
TYPE), variabile (sec]iunea lor `ncepe cu VAR) sau alte proceduri. Acestea din urm\ pot fi
imbricate – adic\ o procedur\ poate cuprinde pe alta [.a.m.d. Doar instruc]iunile procedurii
respective [i eventualele alte proceduri interioare pot folosi ceea ce e declarat local, la
`nceputul ei. Declara]iile de clase de obiecte sunt, `n Oberon, declara]ii de tipuri de date, cu
men]iunea c\ vom vedea mai t=rziu cum se ata[eaz\ acestor tipuri procedurile necesare.
Clasele sunt deci plasate `ntr-o sec]iune care `ncepe cu TYPE.
~ntruc=t serviciile unor module sunt apelate de obicei de alte module iar apelul nu se face
numai o dat\, majoritatea instruc]iunilor sunt plasate `n proceduri, [i NU `n finalul modulelor,
acolo unde este secven]a de ini]ializare. Nu uita]i: acele instruc]iuni finale se execut\ doar o
dat\, la `nc\rcarea modulului.
Cuvinte cheie: limbaje formale, identificator, operator, string, separator, designator, format
eponenţial, domeniu de vizibilitate, pointer, record, cuvinte rezervate,identificatori predeclaraţi,
export, identificatory read-only * , - ,
De studiul riguros al unui limbaj cu mijloace `mprumutate din matematic\, `n special din
algebr\, se ocup\ teoria limbajelor formale. Ca orice obiect matematic limbajul este definit
pe baza unor nota]ii stricte, care descriu cum arat\ diverse componente ale limbajului:
vocabularul, sintaxa, semantica. Pragmatica nu este complet formalizat\ iar `n domeniul
semanticii mai este `nc\ de lucru. Aceste defini]ii formale sunt at=t de riguroase [i de clare
`nc=t un cunosc\tor ajunge s\ prefere o descriere a sintaxei unui limbaj pe c=teva pagini,
uneori pu]in mai mult de zece, `n locul unui manual voluminos, pe care `l va consulta doar la
nevoie. Teoria limbajelor formale este considerat\ o ramur\ a matematicii aplicate [i
figureaz\, `mpreun\ cu capitole ale ei `n nomenclatorul de domenii matematice editat de
AMS (Amer.Math.Soc. – celebra societate american\ de [tiin]e matematice).
Exemplific\m asemenea nota]ii formale, `ncep\nd cu cele mai simple no]iuni despre un
limbaj. Antrena]i-v\ s\ le sim]i]i sensul de cum le-a]i citit. La urma urmei sunt [i ele un limbaj.
Limbajul Oberon (mai exact Oberon-2) ca [i alte limbaje folosesc no]iunile de identificator,
num\r, string ([ir de caractere), operator [i delimitator, pentru a numi entit\]ile din
vocabularul limbajului. Aceste no]iuni sunt comune majorit\]ii limbajelor moderne de
programare. Uni autori, inclusiv
H. Mössenböck [i N. Wirth,utilizeaz\ pentru toate aceste categorii luate `mpreun\, no]
iunea de “simboli” sau “simboluri”. Cuv=ntul vine din teoria gramaticilor formale, unde
asemenea cuvinte se numesc “simboluri terminale” ale unui limbaj, spre deosebire de
categorii gramaticale ca <instruc]iune>, <expresie>, <term>, <factor> care sunt numite
Identificatorii se definesc formal ca fiind secven]e de litere [i cifre. Primul caracter dintr-un
identificator e obligatoriu liter\. Liniu]a de subliniere, «_» este considerat\ liter\. Acolada
`nseamn\ c\ ceea ce e cuprins `n ea se poate repeta de oric=te ori. Iar acest ceva este ori o
liter\ ori o cifr\, sensul barei verticale fiind de separare a dou\ alternative posibile. Iat\
defini]ia identificatorilor (nota]ie `n stilul celor din Help-ul Pow).:
Numerele sunt numere `ntregi cu sau f\r\ semn sau numere reale. Tipul la care apar]in
numerele `ntregi este cel mai mic tip care le cuprinde. Numerele `n baza 16 (Hexazecimale,
formate cu cifrele 0-9, A,B,C,D,E,F ) se termin\ cu litera H. ~n lipsa sufixului H, num\rul se
consider\ zecimal.
Numerele reale con]in `ntotdeauna punct [i este exact unul. Dac\ e vorba de numere reale
`n format exponen]ial (care de asemenea e comun multor limbaje), atunci se termin\ cu E
sau D urmat de puterea lui 10 cu care trebuie `nmul]it num\rul, aceast\ putere fiind un
`ntreg cu semn. 1.75E5 `nseamn\ de fapt 175 000. Oberonul consider\ numerele reale
nr = intreg | real .
intreg = cifra {cifra} | cifra {cifraHexa} "H" .
real = cifra {cifra} "." {cifra} [FactorDeScala].
FactorDeScala = ("E" | "D") ["+" | "-"] digit {digit} .
cifraHexa = cifra | "A" | "B" | "C" | "D" | "E" | "F" .
cifra = "0" | "1" | "2" | "3" | "4" | "5" | "6" | "7" | "8" | "9" .
Stringurile sunt secven]e de caractere cuprinse `ntre ghilimele simple ( ‘ ) sau duble ( " ). ~n
Oberon nu conteaz\ cu ce ghilimele scrie]i stringurile, dac\ folosi]i acela[i fel de ghilimele [i
la `nceput [i la sf=r[it. Un al treilea simbol de acest fel nu este permis `n string, deoarece l-ar
for]a s\ se termine mai devreme. Limbajul Pascal folose[te ghilimelele simple (apostrof) iar
C, C^^, Java folosesc ghilimelele duble pentru a `ncadra string-urile. Verifica]i ce fel de
ghilimele se folosesc `ntr-un limbaj pe care `l `nv\]a]i sau dac\ sunt permise ambele variante
de scriere a stringurilor. Personal am senza]ia c\ ghilimele duble vor fi mai populare `n
viitoarele limbaje. Num\rul de caractere al unui string se nume[te «lungimea stringului».
Stringurile de lungime 1 sunt `n Oberon asimilate constantelor caracter. ~n alte limbaje nu
este a[a, de exemplu `n C sau C^^, unde, al nivelul memoriei un caracter ocup\ un octet de
iar stringul terminat cu cod zero ocup\ un caracter `n plus, deci doi octe]i. Ca urmare, sunt
diferite [i au [i nota]ii diferite.
string = ' " ' {char} ' " ' | " ' " {char} " ' ".
Comentariile se scriu `ntre (* [i *) . Pot fi plasate `ntre oricare dou\ simboluri terminale din
limbaj (numere, identificatori, stringuri, operatori, delimitatori). Dac\ sunt totu[i introduse
`ntr-un string (`ncerca]i practic) sunt acceptate ca fiind un text, nu ca un comentariu [i vor
afecta execu]ia programului. Comentariile sunt complet ignorate de compilator, nu afecteaz\
func]ionarea programului. Pot con]ine orice fel de explica]ii `n orice limb\, note de copyright,
semn\tura autorului, etc. ~n Oberon pute]i scrie comentariu `n comentariu sau pute]i
transforma `n comentariu ([i elimina `n acest fel) orice por]iune de program, chiar con]in`nd
alte comentarii.
~ntr-un limbaj de programare modern, orice identificator, al indiferent c\rei entit\]i trebuie mai
`nt=i declarat apoi folosit. Fac excep]ie identificatorii predeclara]i, de exemplu numele
anumitor proceduri incluse `n limbaj (ex: Write di Pascal). Cu ocazia declar\rii sunt
exprimate anumite propriet\]i ale entit\]ii nou introduse: valoarea [i implicit tipul pentru
constante, tipul pentru variabile, numele [i tipul componentelor pentru o `ntregistrare
(RECORD) sau un obiect, tipul elementelor unui vector, structura unui tip de date compus
etc.
1. Un acela[i identificator nu poate referi dou\ entit\]i declarate diferit `n acela[i bloc.
Redeclararea sau dubla declarare nu este permis\ `n acela[i bloc.
2. Orice entitate poate fi folosit\ de programator doar `n domeniul ei de vizibilitate. Nu uita]i
c\ anumi]i identificatori, cei cu stelu]\, pot fi f\cu]i vizibili `nafara modului, mai exact `n alt
modul care import\ modulul respectiv. De acolo ei vor fi referi]i prin construc]ii de genul
NumeModul . Identificator unde numele de modul poate fi [i o porecl\ a modulului. Pute]i
folosi [i simbolul minus (-) `n loc de stelu]\ (*) pentru a exporta identificatori dar `n acest caz
vor fi identificatori “read-only”. Asupra lor se va putea avea acces doar `n citire. De exemplu,
`ncercarea de a atribui valori unei asemenea variabile exportate se soldeaz\ cu un mesaj de
eroare la compilare cum ar fi
« Error 76: this variable (field) is read only».
3. ~n general nu pute]i folosi un tip de date `nainte de a fi declarat sau `nafara domeniului
s\u de vizibilitate, m\car pentru faptul c\ nu se cunoa[te cantitatea de memorie necesar\
unei date de tipul respectiv. Deoarece o adres\ de memorie are `ns\ `ntotdeauna aceea[i
lungime, indiferent a c\rei date este adresa, rezult\ ca un tip POINTER TO <AltTip> poate
fi declarat [i folosit `n afara domeniului de vizibilitate a declara]iei pentru acel <AltTip>.
Practic, putem declara un tip pointer la un tip care va fi declarat mai departe, dar acesta din
urm\ trebuie totu[i declarat `n acela[i bloc. O regul\ despre vizibilitate care `[i are locul `n
acest subcapitol dar se refer\ la no]iuni `nc\ neexplicate este urm\toarea:
4. Identificatorii c=mpurilor (prin c=mpuri `n]eleg componente ale unui RECORD, care se
declar\ la fel ca variabilele) dintr-o `nregistrare sau denumirile procedurilor legate la tip (iar
tipul devine `n acest caz clas\ de obiecte) sunt utilizabili numai `n designatorii acelui tip.
Altfel spus doar dac\ o variabil\ sau o substructur\ a unei structuri de date este de un
Extrage]i din documenta]ia electronic\ sau dintr-un volum despre limbajul
Oberon-2 semnifica]iile [i/sau m\car contextul de folosire pentru fiecare
cuv=nt rezervat [i fiecare identificator predeclarat, astfel `nc=t s\ pute]i
relata ce [ti]i despre el, din ce construc]ie sintactic\ face parte (dac\ e
cuv=nt rezervat) [i ce `nseamn\, apoi la ce este folosit. Ce deosebire g\si]i `ntre
identificatorii predeclara]i [i cuvintele rezervate ? De care dintre aceste categorii nu se poate
lipsi un limbaj ?
Extrage]i din documenta]ia electronic\ sau dintr-un volum despre limbajul
C++ (sau C# sau Java) semnifica]iile [i/sau m\car contextul de folosire
pentru fiecare cuv=nt rezervat [i fiecare identificator predeclarat, astfel
`nc=t s\ pute]i relata ce [ti]i despre el, din ce construc]ie sintactic\ face
parte (dac\ e cuv=nt rezervat) [i ce `nseamn\, apoi la ce este el folosit.
Despre cuvinte cheie, despre secvenţa, IF, CASE, FOR, REPEAT, WHILE, WITH
Defini]ie: Programarea structurat\ const\ `n scrierea programelor din
instruc]iuni simple (atribuiri, apeluri de proceduri, instruc]iuni de I/O) puse
ori una dup\ alta ori incluse unele `n altele. Fiecare mod de a grupa
`mpreun\ mai multe instruc]iuni se face conform unei reguli. Numim o
asemenea regul\ «structur\». Ea ne spune cum s\ `mbin\m structurile mai mici cu un fel de
“mortar” care e format din cuvinte cheie [i alte simboluri ca s\ ob]inem o nou\ structur\.
Teoria calculabilit\]ii a studiat deja c=te structuri sunt necesare pentru realizarea tuturor
programelor posibile: Sunt NECESARE: secven]a, alternativa, o structur\ repetitiv\ (nu
conteaz\ care e, dac\ e cu test final sau cu test ini]ial). A prezenta teorema respectiv\ dep\-
[e[te scopul acestui volum.
~n practic\ `ns\, limbajele de programare, `n dorin]a de a ajuta programatorul `n construirea
instruc]iunilor structurate, ofer\ mai multe reguli. Incluz=nd cea mai simpl\ regul\ (de a scrie
instruc]iunile `n secven]\ una dup\ alta separate prin “ ; ”) l=ng\ celelalte, rezult\
urm\toarea list\ de instruc]iuni structurate:
- Structura alternativ\ (permite s\ execut ceva sau altceva func]ie de o condi]ie) ~n
multe limbaje poart\ numele IF, (sau IF … THEN …ELSE…etc.) Re]ine]i c\ va con]
ine o condi]ie boolean\ [i (cel pu]in) dou\ secven]e de instruc]iuni.
- Structura alternativ\ generalizat\ (permite ca, `n func]ie de valoarea unei expresii
s\ execut una sau alta dintre ni[te instruc]iuni sau secven]e de instruc]iuni. Instruc]
iunuile pot fi [i ele compuse, adic\ structurate. ~n Oberon [i Pascal se nume[te
CASE. ~n alte limbaje (Ex: C [i derivatele), o g\si]i sub numele de «switch» . Pot fi [i
alte denumiri.
Aten]ie: Limbajele obiectuale (adic\ orientate obiect) au permis apari]ia unei noi
structuri alternative, care alege nu dup\ valoarea ci dup\ tipul rezultatului. ~n
Oberon aceasta se nume[te WITH [i este ceva diferit de WITH–ul din Pascal.
Deci cunosc\torii de Pascal vor trebui s\-[i actualizeze cuno[tin]ele despre WITH.
- Bucla cu num\r cunoscut de itera]ii: Acea structur\ care permite s\ programezi
de c=te ori s\ se execute o instruc]iune sau o secven]\ de instruc]iuni. Bucla folose
[te o variabil\ contor care `[i schimb\ valoarea la fiecare pas, iar valoarea ei poate fi
folosit\ `n calcule. ~n multe limbaje se nume[te FOR. Aten]ie, «for»-ul din C este mult
mai puternic [i mai complex dec=t cel din Pascal sau Oberon, put=nd la nevoie ]ine
[i locul urm\toarelor structuri cu num\r necunoscut de itera]ii:
Metafora care descrie acest fenomen de `nghi]ire a unei/unor structuri de c\tre alta mai
mare este: Pe[tele cel mare `nghite pe cel mic. (sau pe cei mici.) Nu uita]i c\ la urma
urmei [i el este `nghi]it de altul. Balena sau rechinul balen\ care i-a `nghi]it pe to]i este de
fapt procedura, func]ia, metoda sau programul principal. Dar deja aici ie[im din cadrul
subiectului: «modul de `mbinare al instruc]iunilor» deoarece procedura poate con]ine [i
altceva dec=t instruc]iuni,de exemplu declara]ii. La fel [i modulul.
DE: denumirea
SI: sintaxa `n Oberon
SE: semantica, explica]iile
EX: un exemplu de folosire
Observa]i c\ prin felul cum este IF `n Oberon, fiecare secven]\ de instruc]iunui este cuprins\
`ntre dou\ cuvinte cheie: THEN …ELSIF, THEN… ELSE sau ELSE … END. Aten]ie: Alte
limbaje (cum este limbajul Pascal) nu permit folosirea lui ELSIF, deci va trebui s\ scrie]i IF-
urile unul `n altul, imbricate. Este o veritabil\ prob\ de programare structurat\, mai ales c=nd
ve]i num\ra END-urile de la sf=r[it!
EX:
IF (ch>="A") & (ch<="Z") THEN ReadIdentifier
ELSIF (ch>="0") & (ch<="9") THEN ReadNumber
ELSIF (ch="'") OR (ch='"') THEN ReadString
ELSE SpecialCharacter
END
Explica]ia exemplului: ~n situa]ia `n care valoarea lui ch este o liter\ din alfabetul cu
majuscule, se va executa procedura ReadIdentifier. ~n cazul c=nd caracterul ch este o
cifr\ de la 0 la 9 se va executa procedura ReadNumber. Iar dac\ valoarea variabilei ch
este una din cele dou\ (feluri de) ghilimele se va executa procedura ReadString. Altfel se
va executa procedura SpecialCharacter.
Structura alternativ\ generalizat\ CASE
DE: CASE … OF …. : … ELSE … END
SI: CaseStatement =
CASE Expression OF
EX: CASE ch OF
"A" .. "Z" : ReadIdentifier
| "0" .. "9" : ReadNumber
| " ' ", ' " ' : ReadString
ELSE SpecialCharacter
END
permite ca, `n func]ie de valoarea unei expresii, care aici este variabila ch, s\ se execute
una sau alta dintre procedurile ReadIdentifier , ReadNumber ,
ReadString sau, `n cazul altui fel de caracter, procedura SpecialCharacter.
Practic: ~ncerca]i s\ stabili]i `ntre ce valori ale contorului a se va «`nv=rti» bucla FOR din
exemplul de mai jos. Observa]i c\ el are dou\ particularit\]i: Pe de o parte contorul este
folosit `n interiorul buclei (ceea ce este permis cu condi]ia s\ nu-i modifica]i valoarea), pe de
Test: dac\ pute]i spune numai pe baza cuno[tin]elor teoretice (de mai sus)
ce numere afi[eaz\ programul, `nseamn\ c\ st=p=ni]i perfect semantica
buclei FOR.
Remarca]i faptul c\ fiecare num\r a fost scris pe trei spa]ii, aliniat la st=nga, acesta fiind un
efect al parametrului al doilea al procedurii WriteInt.
Acea structur\, FOR-ul este deci cea care permite s\ programezi de c=te ori s\ se execute
o instruc]iune sau o secven]\ de instruc]iuni. Bucla folose[te o variabil\ contor care `[i
schimb\ valoarea la fiecare pas, iar valoarea ei poate fi folosit\ `n calcule. Este
recomandabil s\ nu folosi]i valoarea variabilei contor `n calculul celei de-a doua expresii,
rezultatele execu]iei unor asemenea bucle FOR fiind contrare primei impresii. Dac\ totu[i
ave]i nevoie de o bucl\ a c\rei limit\ superioar\ poate fi modificat\ `n cursul rul\rii
programului folosi]i bucla REPEAT … UNTIL , sau WHILE …DO …END.
Sintaxa lui REPEAT…UNTIL ne spune c\ el este format din cuv=ntul rezervat REPEAT
urmat de o secven]\ de instruc]iunui notat\ `n documenta]ie StatementSequence, apoi
cuv=ntul rezervat UNTIL [i expresia Expression care trebuie s\ fie obligatoriu de tip logic
(BOOLEAN). Expresia poate consta [i `ntr-un apel de procedur\ func]ional\, eventual (din
alt modul).
SE: “A repeat statement specifies the repeated execution of a statement sequence until a
condition specified by a Boolean expression is satisfied. The statement sequence is
executed at least once.” A[a o g\si]i explicat\ dac\ apela]i la meniul Help -> Compiler topic
search [i scrie]i cuv=ntul FOR. Explica]ia de mai sus `n traducere adaptat\ `nseamn\:
EX: Bucla repeat until din programul de mai jos va scrie mesajul de salut `ncontinuu, `n mod
repetat, p=n\ va ap\sa cineva o tast\.
Acesta este un caz mai pu]in obi[nuit (de[i `n unele jocuri video simple exist\ asemenea
bucle). De obicei condi]ia buclei REPEAT … UNTIL depinde de unele variabile ale
programului, ale c\ror valori sunt modificate de instruc]iunile din bucl\. Astfel condi]ia
(expresia boolean\) devine adev\rat\ iar bucla ajunge s\ se opreasc\. O bucl\ REPEAT …
UNTIL a c\rei condi]ie nu poate fi modificat\ de instruc]iunuile din bucl\ se va “roti” ori o
singur\ dat\ (condi]ia era deja adev\rat\) ori de un num\r infinit de ori, provoc=nd aparenta
«blocare» a programului.
Re]ine]i deci c\: REPEAT … UNTIL este structura care permite s\ program\m repeti]ia
instruc]iunilor cuprinse `n ea, p=n\ la `ndeplinirea unei condi]ii. ~n multe limbaje, inclusiv
Oberon [i Pascal se nume[te REPEAT … UNTIL . Con]ine o instruc]iune structurat\ sau o
secven]\ de instruc]iuni [i o condi]ie logic\ (expresie boolean\) la sf=r[it. Acolo poate fi [i o
Bucla cu test ini]ial, cunoscut\ [i sub denumirea de bucla WHILE …DO ..END sau pe
scurt bucla WHILE.
Din punct de vedere sintactic se scrie astfel: Cuv=ntul rezervat WHILE urmat de condi]ia
dat\ de expresia boolean\ Expression. Urmeaz\ cuv=ntul rezervat DO [i secven]a de
instruc]iunui StatementSequence terminat\ cu END.
SE: Folosind bucla WHILE …DO …END program\m execu]ia repetat\ a unei secven]e de
instruc]iunui at=ta vreme c=t condi]ia sa este satisf\cut\. Condi]ia este testat\ `naintea
fiec\rei execu]ii a buclei. Observa]i c\ este preferabil s\ existe instruc]iuni `n bucl\ capabile
s\ modifice valoarea condi]iei. Este posibil s\ folosi]i o func]ie (procedur\ func]ional\)
capabil\ s\ returneze un rezultat boolean pe post de condi]ie (sau chiar o expresie boolean\
cu func]ii).
Aceast\ bucl\ caut\ `ntr-o list\ simplu `nl\n]uit\ (sau mai cur=nd pe ramura unui arbore)
elementul t cu cheia i. Cei care au studiat Pascal-ul `nainte vor observa c\ sintaxa Oberon-
ului difer\ doar `n dou\ locuri (`n acest exemplu) de cea a Pascalului (diferit se scrie ca un
diez [i nu ca mai-mic-mai-mare "<>" iar conjunc]ia logic\ se scrie & nu "and" ). Acest
exemplu nu e accesibil acelora care nu au studiat liste [i arbori.
v := low; temp := high;
IF step > 0 THEN
WHILE v <= temp DO statements; v := v + step END
ELSE
WHILE v >= temp DO statements; v := v + step END
END
Despre: tip de date abstract, limbaje orientate obiect (object-oriented), moştenire, (inheritance),
obiect (object), polimorfism, supraîncărcare, verificare dinamică a tipurilor, clasă, instanţă,
metodă, mesaj.
De ce s-a ajuns la programarea orientat\ pe obiecte? Exist\ nevoi reale de a inventa un nou
tip de date, obiectul, pe l=ng\ cele deja existente? Ce aduce el `n plus? De ce mai este
nevoie pentru a modela un col] de univers, transpun=ndu-l `n program de calculator?
~ncerc\m s\ r\spundem la aceste `ntreb\ri, pentru a justifica de fapt urm\toarea:
Defini]ie: Programarea orientat\ obiect este programarea care folose[te
obiecte (transpuneri ale unor entit\]i din universul problemei sau din natur\)
[i mesaje (cereri pe care le fac unele obiecte altora de a realiza ceva).
Mesajele pot fi provocate de ni[te evenimente produse de sistemul de
operare. Obiectele con]in date (cam ca ni[te variabile) [i metode (care sunt de fapt
proceduri sau func]ii ata[ate obiectului). Pentru u[urarea muncii programatorului clasele (`n
fond ni[te tipuri de date nou definite) se grupeaz\ `ntr-o ierarhie de clase, legat\ prin rela]ie
de mo[tenire (astfel c\ o clas\ poate prelua totul de la o clas\ veche [i poate avea [i ceva `n
plus – date sau metode - dar f\r\ s\ se mai scrie din nou `n program ce con]inea clasa
Defini]ie: vectorul sau matricea este o structur\ de date compus\.
format\ din elemente de acela]i tip, f\r\ nume proprii¸ dar accesibile pe
baza indicilor. Indicii pot fi da]i fie sub form\ de constante fie sub form\ de
expresie . Fiecare element poate avea unul, doi, trei sau mai mul]i indici,
dup\ dimensiunea matricii. Vectorul e o matrice unidimensional\. O
matrice bidimensional\ e analogul unui cofraj de ou\ dar nu con]ine ou\ ci date de acela[i
tip. Num\rul de linii nu e neap\rat egal cu cel de coloane. O matrice tridimensional\ v-o
pute]i imagina ca mul]imea cubule]elor care compun un cub asemenea cunoscutelor juc\rii
cubul Rubik sau cubul Soma. ~ntr-un asemenea cub fiecare element (cubule]) are trei indici.
Se pot folosi [i matrici cu mai mult de trei dimensiuni. Memoria ocupat\ de matrici este
propor]ional\ cu produsul indicilor maximi.
Defini]ie: RECORD-ul sau `nregistrarea este o structur\ de date compus\.
format\ din elemente de tipuri diferite, av=nd nume proprii
(identificatori), cu ajutorul c\rora denumim componentele unei astfel de
structuri. Imagina]i-v\ o asemenea structur\ ca o colec]ie de declara]ii de
variabile, scris\ `ntre dou\ cuvinte care o delimiteaz\. (~n Pascal [i Oberon cuvintele sunt
RECORD [i END.)
Orice variabil\ de tipul respectiv (sau `n general orice e declarat de tipul respectiv
va avea componentele declarate, a[a cum orice num\r complex are partea real\ [i cea
imaginar\.) Imagina]i-v\ un RECORD nu ca un cofraj de ou\ (acelea ar fi identice) ci ca pe
trus\ de unelte a me[terului venit s\ v\ dea g\uri `n zid. Valiza lui are ni[te l\ca[uri `n care
se pun: ma[ina de g\urit, o mandrin\ de rezerv\, cheia, un set de burghie, c=teva dibluri [i
[uruburi etc. Fiecare compartiment din valiz\ are forma [i dimensiunea piesei / dispozitivului
Iat\ povestea: Lumea pe care o avem de modelat `ntr-o structur\ de date compus\ este
imaginarul palat al califului din Bagdad. ~n jocul nostru el va fi compus din Camere, fiecare
av=nd o denumire, un artefact, o sum\ de bani [i,4 u[i similare. Imagina]i-v\, pentru u[urin]a
desemn\rii lor c\ aceste camere [i aceste u[i sunt numerotate, de la 0 la 2 (aici vom da ca
exemplu un palat minuscul, cu trei camere) [i de la 0 la 3 pentru cele 4 u[i. Re]ine]i c\ `n
unele limbaje , Oberon, C, C^^, numerotarea elementelor unui vector `ncepe
obligatoriu de la 0. Convenim ca eticheta fiec\rei u[i s\ poarte num\rul camerei `n care d\
u[a respectiv\, num\rul –1 s\ desemneze o u[\ `nchis\, iar num\rul –2 s\ marcheze u[a
care d\ `n de[ert, acolo unde (dac\ a ajuns juc\torul) se `ncheie jocul.
MODULE Calif;
IMPORT Display; (* folosim modulul cu func]ii de Intrare / Ie[ire *)
CONST NrCamere= 3 ;
inchisa= -1 ; (* u[a `nchisa va fi –1 *)
desert= -2 ; (* sala –2 va fi de[ertul *)
TYPE Camera=RECORD
nr : INTEGER ;
nume : ARRAY 30 OF CHAR ; (* String de 30 de caractere *)
artefact : ARRAY 10 OF CHAR ; (* String de 10 caractere *)
usa : ARRAY 4 OF INTEGER ; (* Vector de 4 numere de camere *)
bani : INTEGER;
END ;
Palat=ARRAY NrCamere OF Camera ;
PROCEDURE ProgMain* ;
S\ `ncepem ini]ializarea variabilelor. O poate face at\t procedura principal\ c\t [i modulul la
`nc\rcare. B\nui]i cum este mai avantajos ? Am optat pentru ini]ializare f\cut\ chiar de
procedura principal\. Cu ocazia ini]ializ\rii practic “mobil\m” palatul.
Observa]i c\ am ini]ializat [i variabila salacrt, cu num\rul primei s\li. Observa]i apoi cum
sunt scri[i designatorii din st=nga atribuirilor.
Jocul decurge `n felul urm\tor: De fiecare dat\ computerul ne scrie pe ecran `n ce sal\ am
ajuns, `ntreab\ ce u[\ folosim ca s\ plec\m mai departe, verific\ num\rul u[ii (element de
programare defensiv\) apoi schimb\ num\rul s\lii. Ca efect al schimb\rii, atunci c\nd se reia
bucla principal\, vom vedea c\ suntem `n alt\ sal\. Observa]ie: Trebuie verificate datele
introduse de utilizator [i doar atunci c=nd sunt valide pot fi prelucrate. Bucla principal\ este
o bucl\ WHILE …DO…. Sintaxa instruc]iunii WHILE … DO … este (reamintim):
Instruc]iuneaWhile =
WHILE Expresie DO Secven]\Instructiuni END .
Astfel se programeaz\ ca reluarea secven]ei de instruc]iuni s\ aib\ loc de fiecare dat\ c=nd
«Expresie» se evalueaz\ la TRUE. Dialogul decurge a[a cum se vede `n imaginea
urm\toare iar instruc]iunile sunt:
Iar dup\ introducerea num\rului acesta va fi testat, urm=nd ca abia apoi num\rul de pe
eticheta u[ii s\ devin\ noul num\r al s\lii curente, dovad\ c\ am ajuns `ntr-o nou\ sal\. Iat\
instruc]iunea compus\ IF…THEN …ELSE …END, extins\ cu o ramur\ ELSIF, folosit\ `n
acest scop:
Edita]i programul cu editorul Pow-ului, salva]i modulul Calif.mod, compila]i,
link-edita]i [i rula]i programul. Trebuie s\ pute]i pune `n func]iune acest mic
joc conversa]ional (a[a cum erau `nc\ multe altele pe vremea terminalelor
f\r\ moduri grafice...).
~n figura care urmeaz\ am surprins jocul `n plin\ ac]iune. Deja s-au succedat c=teva
dialoguri `ntre juc\tor [i calculator. Observa]i cum fiecare reluare a buclei folose[te datele
din alt\ structur\ de date (din alt\ camer\) pentru a construi mesajele calculatorului.
~n lipsa unei modulariz\ri acceptabile programele care rezult\ separ=nd datele de proceduri
au tendin]a s\ devin\ mari. Ele au procedurile lungi [i greu de scris. Imbricarea (scrierea
una `n alta a) structurilor program\rii structurate trebuie verificat\ cu grij\, un END uitat
(cum este cel din finalul buclei WHILE), put=nd fi o surs\ de complica]ii. Cu excep]ia tipurilor
de date nu putem refolosi altceva din aplica]ie. Datele formeaz\ un veritabil conglomerat, `n
cazul de fa]\ un vector de record-uri. E adev\rat c\ este adesea util s\ putem stoca toate
datele problemei `ntr-o variabil\ structurat\, dar nu are rost `ntotdeauna s\ grup\m prea
multe date, mai ales c=nd apar]in unor p\r]i diferite ale problemei [i se pot prelucra separat,
pe categorii. Remarca]i faptul c\ e mai natural ca “salacrt” [i “nrusa” s\ NU fac\ parte din
palat, ele fiind informa]ii care-l privesc pe juc\tor. Lucru de care am ]inut cont c=nd am scris
programul, declar=ndu-le ca variabile distincte. Vom vedea c\ se poate merge mai departe
cu aceast\ abordare.
Exemplu:
Exemplu:
Sintaxa instruc]iunii LOOP… END este foarte simpl\. Deoarece bucla LOOP … END are o
instruc]iune explicit\ de p\r\sire a buclei, nu mai este nevoie s\ aib\ o condi]ie (test) nici la
`nceput (test ini]ial) nici la sf=r[it (test final). Prin urmare expresia boolean\ pe care o
`nt=lnea]i la buclele WHILE… DO …END [i REPEAT … UNTIL lipse[te iar bucla are
sintaxa:
LoopStatement =
LOOP StatementSequence END
Semantica: Folosind bucla LOOP … END program\m computerul s\ execute `n mod repetat
(teoretic la infinit) instruc]iunile din secven]\. Execu]ia unei instruc]iunui EXIT opre[te
bucla, transfer=nd controlul execu]iei la prima instruc]iune de dup\ bucl\. Exemplu:
LOOP
Display.ReadInt(n,3,error);
IF n < 0 THEN EXIT END;
Display.WriteInt(n,3)
END
Este bucla care cite[te numerele `ntregi date de utilizator [i le afi[eaz\, oprindu-se la
`nt=lnirea unui num\r mai mic dec=t zero, care r\m=ne neafi[at.
Obligatoriu, structura LOOP … END va trebui s\ con]in\ o alt\
structur\ alternativ\, care la r=ndul ei va con]ine printre alternative
instruc]iunea EXIT. ~n exemplul de mai sus, structura alternativ\ este IF…
THEN…END. ~n lipsa unei asemenea structuri ave]i ori o bucl\ care se
opre[te de prima dat\ (deoarece con- ]ine un EXIT, ori o bucl\ ce se va executa la infinit,
deoarece nu con]ine nici unul. Re]ine]i c\: instruc]iunea LOOP…END `[i arat\ utilitatea la
programarea acelor repet\rii de secven]e de instruc]iuni care au mai multe puncte de ie
[ire sau la cele la care punctul de ie[ire este `n mijlocul secven]ei ce se repet\.
Exerci]ii:
1.Rescrie]i jocul de mai sus, folosind bucla LOOP …END.
2. Ad\uga]i o variabil\ pentru colectarea banilor care se g\sesc `n s\lile
palatului. Valoarea ei va fi m\rit\ automat la intrarea `ntr-o nou\ sal\ iar din
acel moment suma r\mas\ `n sal\ va fi zero. Not\: Cele dou\ exerci]ii pot fi lucrate `n orice
ordine, independent sau simultan.
Despre sec]iunea TYPE a unei proceduri sau a unui modul: Ea con
]ine declara]ii de tipuri a[a cum sec]iunea VAR con]inea declara]ii de
variabile. Sec]iunea `ncepe cu TYPE. Urmeaz\ perechi de forma
identificator [i descriere de tip. ~ntre identificator [i descriere este
semnul egal (nu ':' ca la declara]iile de variabile). Descrierile de tip pot con]ine alte
descrieri de tip [.a.m.d, dup\ principiul pe[telui care a `nghi]it alt pe[te. Un tip care
poart\ un nume se nume[te tip nominal. Dac\ o variabil\ este declarat\ ca fiind de un
tip compus iar acest tip nu are nume, el se nume[te tip anonim. {i `n limbajele din
familia C-ului exist\ declara]ii de tipuri (cu nume dat de utilizator). Se scriu cu typedef.
Func]ia este pentru matematicieni o rela]ie `ntre dou\ mul]imi de valori. Pe de o parte
valorile (grupate) ale argumentelor [i, pe de alt\ parte – corespunz\tor fiec\rui set de
argumente – valoarea func]iei. Pentru un programator care lucreaz\ `ntr-un limbaj imperativ,
func]ia (v\zut\ `n cel mai simplist mod cu putiin]\) este ceva asem\n\tor: un mod de a
calcula un rezultat pornind de la un set de valori date. Iat\ un exemplu:
Pentru matematician: f:R -> R prin rela]ia f(x) = x+1 este o func]ie. Remarca]i c\ el
trebuie s\ noteze despre ea urm\toarele elemente:
- Numele func]iei : f
- Tipul argumentului , mul]imea din care argumentul ia valori: R
- Tipul rezultatului: R
- Denumirea formal\ a argumentului : x
- {i la urm\ dar nu lipsit\ de importan]\, formula de calcul a rezultatului: x+1
Pentru un programator care transcrie func]ia `n tr-un limbaj de programare, de exemplu
limbajul Oberon, situa]ia este foarte asem\n\toare. La r=ndul s\u, va trebui s\ specifice
practic acelea[i elemente, dar `n limbajul de programare. Ordinea lor este doar pu]in diferit\.
C=rcota[ii vor replica : Este posibil s-o scriem mai simplu ! Le dau dreptate, func]ia de mai
sus se putea implementa sub forma:
MODULE FactRec;
IMPORT Display;
PROCEDURE Fact(n:INTEGER) :INTEGER;
VAR prod :INTEGER;
BEGIN
IF n=0 THEN
prod :=1
ELSE
prod :=n * Fact(n-1)
END;
RETURN (prod)
END Fact;
PROCEDURE ProgMain*;
VAR k:INTEGER;
BEGIN
FOR k:= 1 TO 10 DO
END FactRec.
Nota]i c\: Demonstrarea corectitudinii felului cum calculeaz\ un rezultat o func]ie recursiv\
trebuie f\cut\ prin induc]ie matematic\.
C=teva observa]ii privitoare la folosirea func]iilor de acest fel (la care parametrul sau
parametrii sunt declara]i `n antetul func]iei f\r\ cuv=ntul VAR !):
Important: Dac\ parametrul a fost o variabil\, valoarea acestuia nu este afectat\, orice ar fi
f\cut func]ia cu variabila ei x. (~n fond x e o alt\ variabil\ dec=t cea transmis\ ca argument
func]iei!).Re]ine]i c\ `n cazul transferului parametrilor prin valoare, procedura care
implementez\ func]ia (sau orice procedur\ care primeste datele prin mecanismul de
transfer prin valoare) nu poate modifica datele primite ci lucreaz\ cu copii ale acelor valori.
MODULE Schimbare;
IMPORT Display;
PROCEDURE ProgMain*;
VAR x,y :INTEGER;
BEGIN
x :=3; y :=5;
Schimb(x,y);
Display.WriteInt(x,2);
Display.WriteInt(y,2);
REPEAT UNTIL Display.KeyPressed()
END ProgMain;
END Schimbare.
Spre marea surpriz\ a elevului de care povesteam, execu]ia programului duce la un rezultat
neasteptat, x are tot valoarea 3, iar y tot valoarea 5.
Solu]ia este simpl\, declara]i parametrii procedurii schimb\ ca fiind parametri variabil\,
transmi[i prin referin]\ (sinonim). Se scrie un VAR `naintea listei parametrilor viza]i. Acum
procedura va ar\ta a[a:
Am vorbit `n acest capitol despre func]ii [i implementarea lor apoi am trecut la proceduri.
Oberon [i C nu fac deosebire ca limbajul Pascal `ntre func]ii (FUNCTION) [i proceduri
(PROCEDURES). ~n Oberon toate sunt numite proceduri. Iar `n limbajele din familia C-ului
toate sunt numite func]ii !! E drept, unele posed\ un tip (al rezultatului) declarat, con]in
instruc]iunea RETURN [i pot fi apelate din expresii, fiind numite `n Oberon “function
procedure”, ceea ce am tradus prin proceduri func]ionale. Celelalte nu au un tip declarat al
rezultatului iar dac\ folosesc RETURN (far\ expresie dup\ el) `l folosesc doar pentru a
programa astfel terminarea imediat\ a procedurii. ~n C, “return” se scrie cu minuscule.
O prezentare scurt\ dar bine f\cut\ a procedurilor g\si]i `n Help-ul mediului de programare
POW. ~n continuare o vom traduce [i o vom comenta, comentariile fiind `n paranteze:
Pe l=ng\ entit\]ile locale [i parametrii formali (a[a cum sunt ei declara]i `n antetul
procedurii), alte entit\]i (de obicei variabile) existente `n exteriorul procedurii (deci `n
procedura exterioar\ sau `n modulul ce o cuprinde) sunt de asemenea vizibile [i deci
utilizabile de c\tre instruc]iunile procedurii. Excep]ie fac acele entit\]i din exterior care au
acelea[i nume ca entit\]ile declarate local.
Apelul procedurilor se face astfel: Din acela[i modul: Scrie]i numele procedurii [i lista de
parametri actuali. Din alt modul: Scrie]i numele sau aliasul (porecla) modulului care g\zduie-
[te procedura, operatorul punct , identificatorul procedurii [i lista de parametri. ~n acest caz
identificatorul procedurii trebuie marcat cu *, la prima apari]ie `n declara]ie (nu [i la finalul
procedurii). La fel [i la procedurile func]ionale apelate din expresii.
Defini]ie: O clas\ de obiecte este un nou tip de date. De fapt un tip de
date obiect este un tip RECORD (`nregistrare) care pe l=ng\ componentele
statice (datele) mai are ni[te componente dinamice (metodele). Este
suficient s\ g\sim o modalitate de a descrie metodele `n limbajul de
programare – ceea ce se face scriind proceduri [i apoi s\ ata[\m aceste proceduri tipului
de date RECORD care astfel va deveni obiect. Mai `nt=i trebuie cunoscute c=teva
generalit\]i despre obiecte.Ideea central\ este: OBIECTE = RECORD-uri + Proceduri
~n Oberon spre deosebire de alte limbaje moderne mai s\race, sunt posibile dou\ moduri de
a ata[a procedurile de un record:
a) RECORD-ul este indicat ca receptor (receiver) al unei proceduri legate la tip. Aceasta `i
devine ata[at\, devenind metod\. Toate obiectele unei clase au ata[ate acelea[i proceduri.
De aceea se spune c\ ele sunt legate de tipul de date (clasa) nu de un obiect anume din
acea clas\.
b) RECORD-ul con]ine c=mpuri procedurale, acele c=mpuri a c\ror valoare nu este un
num\r un string ci un nume de procedur\. Exist\ o restric]ie aici: E vorba de proceduri av=nd
aceea[i semn\tur\,(acelea[i tipuri la parametri [i rezultat) lucru de altfel normal deoarece
denumirea c=mpului se va comporta ca un alias al acelei proceduri. Vom putea pune
procedura din record la treab\ chem=nd-o dup\ numele c=mpului procedural [i d=ndu-i
parametri. Ace[tia `i vor fi transmi[i exact procedurii a c\rui nume e stocat `n c=mp. Re]ine]i
deci c\ vom `nt=lni un nou tip de date a c\rui valoare este o procedur\ (cu o anumit\
semn\tur\ dat\ din momentul declar\rii c=mpului). Astfel se pot realiza obiecte din aceea[i
clas\ dar care, sub un nume de metod\ comun ascund algoritmi diferi]i de la un obiect la
altul. Nota]i [i faptul c\ `n C (C++) `n locul c=mpurilor procedurale folosim pointeri la func]ii.
Sintactic vorbind se scriu ca ni[te proceduri obi[nuite care prelucreaz\ un
parametru de tip RECORD, declarat cu VAR. (Vom vedea c\ asemenea
parametri declara]i cu VAR pot fi modifica]i ca efect al instruc]iunilor din
procedur\.) Iat\ un exemplu de procedur\ care afi[eaz\ ziua luna [i anul na
[terii unei persoane, presupuse a fi stocate `ntr-un RECORD cu componentele respective.
Declara]ia tipului RECORD numit DataNa[terii o scrie]i dumneavoastr\. Variabila se putea
s\ fie declarat\ a[a: VAR pers : DataNa[terii. (Observa]ie: Am scris cu [ de[i nu e din
alfabetul limbajului !)
Pentru a lega procedura la tip trebuie s\-i punem `n antet tipul de date la care se leag\ [i s\
preciz\m cum se va numi, `n corpul procedurii, obiectul respectiv. Unele limbaje au o
denumire generic\ pentru obiectul `nsu[i: de exemplu `n C^^ aceasta este this iar acest this
este un pointer la obiectul `nsu[i aflat chiar `n structura lui. Oberon permite s\ numi]i obiectul
`nsu[i cu orice nume (identificator) de variabil\, iar aceasta trebuie declarat\ cu VAR [i
plasat\ `ntr-o parantez\ ~NAINTEA numelui procedurii dar DUP| cuv=ntul rezervat
PROCEDURE. Procedura de mai `nainte s-ar rescrie, dac\ o leg\m la tipul DataNa[terii,a[a:
Ideea centrală este: a ne imagina aplicaţia ca fiind formată din obiecte capabile să facă ceea ce au
de făcut.
S\ ne imagin\m palatul califului format din s\li iar aceste s\li `nzestrate cu capacitatea de a
interac]iona cu noi, cu alte cuvinte de a se juca cu noi. Fiecare sal\ va fi un obiect [i va
avea metode: O metod\ Init pentru ini]ializarea datelor din obiect (un constructor, dar apelat
explicit) [i o metod\ Play care surprinde desf\[urarea jocului `ntr-o camer\ din palat, cu tot
dialogul.
Practic `n clipa `n care dispunem de obiecte din clasa Camera, capabile s\ «se joace» cu
noi, programul principal devine extrem de simplu. Dup\ ini]ializarea obiectelor (care se va
face cu metoda Init a fiec\rui obiect) este suficient s\ stabilim drept camer\ curent\ camera
ini]ial\ [i s\ apel\m metoda Play pentru camera curent\ (salacrt). Metoda va actualiza,
modific=nd dac\ este cazul, num\rul s\lii curente pe care-l prime[te ca parametru variabil\.
Programul principal este practic concentrat `n c=teva r=nduri:
salacrt:=0;
WHILE TRUE DO
p[salacrt].Play(salacrt)
END
Not\: variant\ de mai sus corespunde unui joc jucat la infinit, f\r\ acea ie[ire `n de[ert
(codificat prin –2). ~n acest al doilea caz ar fi fost:
salacrt:=0;
S\ coment\m programul, realizat de data aceasta `ntr-un mod bazat pe obiecte, singura
clas\ fiind clasa Camera, iar obiectele folosite ca elemente ale vectorului Palat. (Afl\m deci
c\ se pot declara [i vectori de obiecte, tipul de dat\ obiect put=nd participa la creare de date
complexe, structurate.) Declara]iile ini]iale sunt la fel, cu observa]ia c\ vom ad\uga ulterior
procedurile (metodele) necesare transform\rii tipului de date Camera `n clas\ de obiecte.
MODULE PalatObj;
IMPORT Display;
TYPE Camera=RECORD
Nr : INTEGER;
Denumire : ARRAY 30 OF CHAR;
Artefact : ARRAY 20 OF CHAR;
Bani : INTEGER;
Usa : ARRAY 4 OF INTEGER;
END;
Palat=ARRAY 6 OF Camera;
Constructorul, procedura de ini]ializare pentru tipul de date Camera, ar putea ar\ta ca mai
jos. Ea prime[te informa]iile ca parametri [i le stocheaz\ `n obiect. Remarca]i cum se
face copierea unui string, liter\ cu liter\, cu ajutorul unei bucle FOR. Unele limbaje au o
func]ie sau o procedur\ proprie pentru a realiza asemenea copieri de stringuri. ~n C se nume
[te «strcpy». ~n Oberon, o colec]ie de proceduri care fac opera]ii cu stringuri g\si]i `n
modulul Strings.
Valorile date ca parametri actuali vor fi `n final stocate `n c=mpurile obiectului X. B\nui]i c\
X va fi `nlocuit cu p[0], elementul cu indicele zero din vectorul palat.
Ce mai [tiu s\ fac\ obiectele noastre din clasa Camera? S\ se joace cu juc\torul uman.
Scriem instruc]iunile respective, grupate `ntr-o procedur\ pe care o vom numi chiar Play
(`nseamn\ joc `n englez\, dar pute]i s\-i da]i [i un nume autohton, ceea ce e chiar indicat,
deoarece face programul mai u[or de citit):
Ca de obicei, num\rul de pe eticheta u[ii indic\ sala destina]ie, aceasta fiind conven]ia dup\
care am realizat planul palatului. Ea asigur\ astfel leg\tura `ntre s\li. Remarca]i [i c=t de
mult s-au simplificat designatorii. Nici vorb\ de
P[salacrt].Usa[nrusa]
PROCEDURE ProgMain*;
VAR p: Palat; (* e un vector de obiecte de tip Camera*)
salacrt:INTEGER;
BEGIN
p[0].Init(0,"Sala de intrare", "strajer", 100, -1,-1,-1,1);
p[1].Init(1,"Sala de judecata", "cadiu",200,-1,0,4, 2);
p[2].Init(2,"Sala armurilor", "pumnal", 500,-1,1,5,3);
p[3].Init(3,"Sala de mese", "oaspete", 1000, -1, 2, -1,-1);
p[4].Init(4,"Sala cu tezaur","tezaur", 10000, 1,-1,-1,5);
p[5].Init(5,"Sala de arme", "jungher", 300, 2,4,-1,-1);
salacrt:=0;
WHILE TRUE DO
p[salacrt].Play(salacrt)
END
END ProgMain;
END PalatObj.
Remarca]i ce simpl\ este descrierea unui palat cu 6 s\li! Doar 6 r=nduri de program, nu
aproape 50! De asemenea, jocul propriu-zis este mult simplificat, deoarece la acest nivel tot
ce am de f\cut este s\ apelez metoda Play a s\lii curente [i s\-i dau drept parametru de
prelucrat tocmai variabila salacrt, `n vederea modific\rii. Observa]i c\ `n procedura Play,
parametrul salacrt este declarat cu un VAR `n fa]\, ceea ce `nseamn\ (conform unei
conven]ii care exist\ [i `n Pascal), exact c\ procedura poate MODIFICA valoarea acestei
variabile date ca parametru [i nu va lucra cu o copie a ei ci cu `ns\[i variabila transmis\.
Expresia `n limba englez\ care denume[te tipurile procedurale este: «Procedure types». ~n
documenta]ia electronic\ (a mediului Pow) o g\si]i `n dreptul cuv=ntului rezervat procedure,
unde este a doua pe lista de no]iuni legate de acest cuv=nt.l Textul inclus ca explica]ie este
scurt:
Ceea ce `n traducere s-ar transcrie a[a: Variabilele de un tip procedural T pot avea ca
valoare o procedur\ sau constanta NIL (care `nseamn\ “nimic”). Dac\ o procedur\ P este
atribuit\ ca valoare a unei variabile de un asemenea tip T, lista parametrilor formali ai
procedurii [i lista parametrilor formali din declara]ia tipului T trebuie s\ se potriveasc\. P nu
poate fi o procedur\ predeclarat\ [i nici o procedur\ legat\ la tip sau o procedur\ interioar\
alteia.
Practic descrierea unui tip procedural poate fi ori cuv=ntul PROCEDURE f\r\ nume sau
parametri, ori cuv=ntul PROCEDURE neurmat de numele procedurii dar cu o list\ de
parametri formali. {tim deja c\ la proceduri, felul cum numim parametrii este nerelevant,
deci cea ce conteaz\ este tipul lor [i ordinea acestor tipuri `n antetul procedurii.
Iat\ cum ar putea ar\ta vechiul program cu palatul califului dac\ am utiliza c=mpuri
procedurale pentru a `nzestra fiecare camer\ din palat cu o procedur\ “Int`mplare” - diferit\
MODULE camere;
IMPORT Display,S:=Strings;
TYPE
Actiune=PROCEDURE (*fara nume*) (expnum:INTEGER);
Camera*=RECORD
nr*:INTEGER;
nume*: ARRAY 30 OF CHAR; (* String de 30 de caractere *)
obiect*: ARRAY 10 OF CHAR; (* String de 10 caractere *)
usa*: ARRAY 4 OF INTEGER; (* Vector de 4 numere de camere *)
bani*:INTEGER;
intamplare*: Actiune; (* Camp procedural *)
END;
PROCEDURE AiciEste*(c:Camera);
BEGIN
Display.WriteStr("Esti in camera nr:");
Display.WriteInt(c.nr,xxx);
Display.WriteStr("Aceasta este ");
Display.WriteStr(c.nume);
Display.WriteStr("Aici gasesti un:");
Display.WriteStr(c.obiect);
Display.WriteStr("Sunt si bani in numar de;");
Display.WriteInt(c.bani,xxx);
END AiciEste;
PROCEDURE Fantome*(expnum:INTEGER);
VAR nrmagic,i:INTEGER; cuvant:ARRAY 10 OF CHAR; err:CHAR;
BEGIN
Display.WriteStr(" Te sperie niste fantome.");
Display.WriteStr(" Trebuie sa le spui de cateva ori fraze magice. ") ;
nrmagic:=expnum MOD 3 +1 ;
FOR i:= 1 TO nrmagic DO
Display.ReadStr(cuvant,10,err);
END;
Display.WriteStr("Fantomele te lasa sa pleci");
END Fantome;
PROCEDURE Tezaur*(expnum:INTEGER);
VAR
BEGIN
Display.WriteStr("Tezaurul te orbeste cu stralucirea lui.")
END Tezaur;
END camere.
END Calif.
Exerci]iu: Reface]i aplica]ia `n Oberon utiliz=nd ambele tehnici de ata[are
a metodelor de RECORD-uri, pentru a le transforma `n obiecte: proceduri
legate la tip pentru constructor [i metodele unice respectiv c=mpuri
procedurale pentru metodele care difer\ de la o instan]\ la alta a
obiectului din clas\ camera.
Exerci]iu: Reface]i aplica]ia `n C++ utiliz=nd ambele tehnici de ata[are a
metodelor de RECORD-uri, pentru a le transforma `n obiecte: metode
implementate ca func]ii [i constructori ai clasei (pentru constructor [i
metodele comune tuturor obiectelor clasei) respectiv pointeri la func]ii
pentru metodele care difer\ de la o instan]\ la alta a obiectului din clasa camera. Pentru
detalii de implementare folosi]i [i fi[ele de laborator dac\ le ave]i la dispozi]ie.
Sau cum pune programatorul unui univers format din oricîte obiecte ordine în haos.
A fi realizatorul unei aplica]ii realizate prin metodele program\rii orientate obiect este, am
putea zice, mai mult sau mai pu]in un act aproape demiurgic. {i ca un veritabil st\p=n al
lumii create, programatorul va trebui s\ [tie cum s\ comande ( a se citi - «s\ instruiasc\
computerul») s\ creeze un nou obiect (`n englez\: NEW object), s\ distrug\ un obiect ([i ve]i
vedea c\ de distrugere – a se citi «dealocarea memoriei» se ocup\ alt «dr\cu[or» numit
Garbage Collector) [i ceea ce este foarte important, s\ fie capabil s\ nu piard\ leg\tura cu
niciunul dintre obiectele create. Pentru aceast\ din urm\ treab\ este nevoie de o structur\
de date flexibil\, care se poate lungi oric=t sau scurta dup\ nevoie, pe m\sur\ ce obiectele
sunt create sau distruse. Cea mai simpl\ structur\ de date de acest fel este LISTA iar cel
mai simplu mod de a o implementa este s\ integr\m `n fiecare RECORD sau obiect ceva
care s\-l indice pe urm\torul. Acel ceva va fi POINTERUL.
Fire[te, cunosc\torii Pascalului vor observa c\ exist\ [i metode mai avansate de a g\si un
element dintr-un univers dat, de exemplu organizarea obiectelor sub form\ de arbore de
c\utare. Dar m\ `ndoiesc c\ o vor face. Manualul de Informatic\ de liceu al domnului Tudor
Sorin (foarte popular datorit\ reclamei de pe copert\ `n care scrie c\ este aprobat ...etc) are
niscaiva lipsuri `n acel capitol ceea ce face ca arborii s\ fie un subiect mai greu de `n]eles,
Re]ine]i totu[i ideea central\: Un nivel (modul) al unei aplica]ii care con]
ine o clas\ de obiecte poate avea acces la toate aceste obiecte dac\
este organizat ca o list\. Lista e util\ [i pentru a transmite un mesaj
(care poate fi un apel de metod\) tuturor obiectelor. Toate obiectele
vor primi mesajul [i dup\ caz vor r\spunde `ntr-un fel sau altul ori ... nu vor r\spunde
deloc.
Dar mai `nt=i s\ vedem cum se programeaz\ «na[terea» RECORD-urilor sau a obiectelor [i
modul cum putem indica (`n englez\ se spune: to point – ceea ce ar trebui s\ v\ dea o idee)
un obiect (variabil\) care fiind nedeclarat(\) nu are un identificator (nume) al ei. ~n acest caz
singurul lucru care poate referi variabila este adresa ei din memorie. Iar pentru a o putea
folosi corect ar fi bine s\ [tim ce tip de dat\ exist\ acolo, la acea adres\. Vom vedea c\
aceste adrese (imagina]i-v\ c\ sunt `nso]ite de o informa]ie de tip) formeaz\ un tip pointer
(tipul pointerilor care indic\ acel fel de date). Despre ei vorbim `n paragrafele urm\toare:
Sau cum fac programatorii şi programele care au mereu nevoie mereu de alte variabile. Cuvinte
cheie: alocare,pointeri, variabile dinamice, NEW, DISPOSE, NIL.
Hei! Ce e nou aici? {tim c\ a urma urmei putem declara oric=te variabile dorim noi `ntr-un
program. Ce aduce nou povestea aceasta? Doar un mic, periculos de mic, am\nunt:
`ntotdeauna p=n\ acum num\rul de variabile utilizate `n program era fix, b\tut `n cuie, iar
programul putea prelucra numai acele variabile, deci o cantitate finit\ de informa]ii, stabilt\
clar din momentul scrierii sale. Evident asemenea programe sunt limitate la a prelucra
informa]ii despre ni[te universuri destul de statice. Un asemenea program n-ar putea ]ine
eviden]a culorilor frunzelor dintr-un arbore ori dintr-o p\dure , a greut\]ilor puilor ie[i]i din ou
la sec]ia «Incubatoare» sau lista clien]ilor unei firme `n dezvoltare. Ambele din acela[i motiv:
mul]imea informa]iilor de gestionat este `n cre[tere continu\, nu se [tie c=t de mult va cre[te
[i nici nu i se poate da u[or o margine dinainte. La asemenea probleme a ap\rut nevoia de
variabile noi. ~nainte, c=nd aveam de scris mici programe [tiam cu c=te variabile lucr\m.
Surprinz\tor este faptul c\ dac\ lua]i sursele programelor dintr-un proiect serios, care face o
chestie util\, ave]i foarte multe [anse s\ g\si]i c\ s-au folosit variabile dinamice .
Observa]ie despre nume: Noile variabile care se nasc prin aceast\ opera]ie de alocare a
memoriei nu pot s\ aib\ nume, nefiind declarate. ({tim deja c\ numele de variabile sunt
citite de compilator din textul programului.) Ele vor fi g\site pe baza adresei lor `n memorie.
Defini]ie: O asemenea adres\, `nso]it\ de o informa]ie despre tipul
datei care exist\ acolo, `n memorie, o vom numi pointer. Aceast\
pereche inseparabil\ este stocat\ `ntr-o alt\ variabil\ , `ntr-un c=mp al
unui record, al unui obiect sau `ntr-o alt\ structur\ de date. Tipul
acestei variabile se nume[te generic tot pointer, de[i `n practic\ se declar\ tipuri de date
distincte dup\ tipul informa]iei indicate de pointer. Spre deosebire de Pascal limbaj `n care
se puteau declara pointeri la aproape orice tip de date, OBERON este mai restrictiv. Se
Contrar ideilor din unele manuale sau lec]ii de la liceu care prezentau pointerul ca o adres\
[i at=t, v\ rog s\ v\ imagina]i pointerul ca o pereche format\ din adres\ [i tip. Adresa ne
spune unde se afl\ `n memorie ceea ce ne intereseaz\ iar informa]ia despre tip ne spune
ce tip de dat\, (care poate fi [i un obiect) g\sim acolo.
Observa]ie despre na[terea variabilelor: Dac\ programul `[i produce singur oric=te variabile
care nu apar `n declara]ii atunci singurul loc unde poate face aceasta este `ntr-o secven]\
de instruc]iuni, printre care exist\ una anume pentru acest scop. (Nu uita]i c\ programele
con]in `n principiu declara]ii care spun ce entit\]i exist\ [i instruc]iuni care fac ceea ce este
de f\cut cu datele.) Prin urmare exist\ neaparat o instruc]iune pentru creat variabile.
Aceasta este `n Oberon (ca [i `n Pascal) NEW(p). ~n C se scrie cu minuscule:new. Litera p
din parantez\ are rolul de a v\ aminti c\ NEW prime[te ca parametru o variabil\ de tip
pointer. Imagina]i-v\ o asemenea variabil\ p ca o cutie `n care pute]i pune o adres\ [i o
informa]ie de tip. Intuitiv vorbind, NEW(p) prime[te o asemena cutie p spre a o umple cu
adres\ [i tip.
Ce face de fapt NEW ? G\se[te o por]iune din memorie liber\ (nu `ntreba]i cum, de
acest lucru se ocup\ mecanismele de alocare a memoriei `ncorporate `n limbaj iar algoritmii
pot fi destul de sofistica]i) apoi plaseaz\ adresa respectiv\ `n variabila care i-a fost
transmis\ lui NEW. ~n exemplul nostru ar pune adresa `n variabila p. Dac\ nu-i reu[e[te
alocarea – ceea ce s-ar putea `nt=mpla `n anumite situa]ii c=nd memoria este epuizat\,
c=nd buc\]ile de memorie liber\ sunt prea mici sau c=nd a avut loc o alt\ eroare – valoarea
special\ stocat\ `n variabila pointer este NIL.
NIL este un fel de zerou al mul]imii pointerilor. Un programator profesionist (care lucreaz\ `n
stil defensiv) va testa o dac\ valoarea unei asemenea variabile este diferit\ de NIL [i abia
apoi ar folosi valoarea pentru a accesa obiectul sau structura de date de la acea adres\.
Cu ce pute]i asem\na activitatea lui NEW ? Intuitiv, cu cea a unui chelner de restaurant
care caut\ o mas\ pentru clientul ce-o solicit\ (atunci c=nd acesta, telefonic, solicit\ o
rezervare). Chelnerul afl\ din eviden]ele lui ce va fi liber, marcheaz\ locul ca fiind ocupat
apoi comunic\ clientului unde [i de ce fel este masa, zic=nd: «Ave]i rezervat\ o mas\ de 4
persoane, masa 7, prima la dreapta cum intra]i pe u[\.» sau «V\ putem oferi o mas\ de
patru persoane `n separeul al doilea.»
DISPOSE(p). Este instruc]iunea invers\ lui NEW(p). Prime[te ca argument o valoare a unui
pointer, diferit\ de NIL. Dealoc\ (elibereaz\) explicit memoria ocupat\ de obiectul sau
structura aflat\ la acea adres\. Mo[tenit\ din Pascal [i p\strat\ mai mult pentru o anumit\
compatibilitate, aceast\ instruc]iune nu mai este obligatoriu de folosit `n Oberon deoarece
acest din urm\ limbaj are `ncorporat un mecanism care face singur dealoc\rile, atunci c=nd
este `n criz\ de spa]iu sau are nevoie. Acest mecanism are un nume destul de prozaic:
«Garbage collector» - «colectorul de gunoaie». Avantajul este c\ el func]ioneaz\ automat
iar programatorul scap\ de grija de a mai dealoca cu DISPOSE() ceea ce a alocat cu NEW
(). Imagina]i-v\ acela[i chelner zelos preg\tind imediat masa pentru al]i viitori clien]I, dup\
plecarea celor care [i-au terminat consuma]ia, f\r\ ca ei. s\-i comande explicit acest lucru
Observa]ie privitoare la limbajele moderne: tot mai multe au tendin]a s\ foloseasc\ aceste
mecanisme de dealocare automat\ ( Garbage collector ).
Comentarii despre folosirea unui pointer la un tip simplu `n Pascal (a[a ceva nu se
mai poate face `n OBERON dar ve]i vedea c\ nu pierdem mai nimic ):
Asemenea pointeri nu-s spectaculo[i, ba par chiar incomozi ([i mul]i cititori ai c\r]ilor de
informatic\ r\m=n cu aceast\ fals\ impresie, dup\ citirea unui capitol despre pointeri)
deoarece, printre altele, `n exemple ca cel de mai sus, pentru fiecare variabil\ dinamic\ de
un anume tip aveam nevoie de un pointer asociat ei, adic\ de o alt\ variabil\ static\ de tipul
«pointer la acel tip al variabilei dinamice». Aceste variabile trebuiau `ns\ declarate, iar
declara]iile erau `n Pascal, asem\n\toare cu cele din OBERON (numai c\ simbolul «
c\ciuli]\» din Pascal a fost `nlocuit `n OBERON de expresia «POINTER TO»). ~n C se
folose[te o o stelu]\ * pus\ `ntre numele variabilei [i tipul acestuia. ~n exemplul de mai sus
am fi avut nevoie s\ declar\m pointerii P [i Q astfel:
BEGIN
…
NEW(P);
NEW(Q);
…
END;
Re]ine]i c\: fiecare structur\ de date alocate poate fi un RECORD sau un
obiect care s\ con]in\ datele de interes pentru noi (culoarea frunzei din
exemplul anterior) [i `mpreun\ cu acestea, un c=mp pointer la RECORD-ul
sau obiectul urm\tor. Astfel odat\ cu fiecare alocare reu[it\ cu NEW ob]in
[i loc pentru datele mele [i o nou\ «variabil\» capabil\ s\ «pointeze» un alt
obiect (de fapt «variabila» e un c=mp de tip pointer din recordul sau obiectul nou creat).
Adic\ nu mai am de declarat variabila pointer, ea fiind practic creat\ automat `mpreun\ cu
recordul sau obiectul.
Deci variabila de tip pointer care va indica urm\torul obiect sau RECORD este inclus\ `n
record-ul sau obiectul anterior ca un c=mp oarecare. Astfel obiectele sau RECORD-urile se
indic\ unul pe altul iar pentru a-l indica pe primul am nevoie s\ declar doar o singur\
variabil\ pointer:
Unde MyType e tipul pointer la tipul record sau obiect declarat mai `nainte astfel:
TYPE
MyType # POINTER TO MyTypeO;
MyTypeO# RECORD
DataUtila: ….;
P: MyType;
END;
Logic: Dac\ fiecare obiect con]ine exact un pointer c\tre obiectul urm\tor, atunci ele se `n-
[ir\ ca ardeii iu]i pe sfoar\, unul dup\ altul, iar ceea ce ob]inem este o list\. Ce valoare are
ultimul pointer, cel care nu mai indic\ nimic? NIL! Not\: O excep]ie este lista circular\ dublu
`nl\n]uit\, care are `n fiecare obiect doi pointeri, unul arat\ `nainte (spre urm\torul obiect) iar
altul `napoi (spre precedentul obiect). Dac\ `ns\ fiecare obiect are doi pointeri care indic\
spre alte dou\ obiecte noi, iar graful format este conex (nu exist\ obiecte neindicate) [i f\r\
cicluri (nu revenim niciodat\ la un obiect anterior) atunci avem un arbore binar.
A]i mai scris programe cu liste [i sunte]i capabil s\ desena]i o list\ [i elementele ei, pentru a
urm\ri prelucr\rile ? ~ncercui]i mai jos r\spunsul:
DA NU
Dac\ a]i r\spuns DA pute]i s\ri peste povestea piciorului, care urmeaz\, dar re]ine]i c\ cel
mai sigur mod de a nu gre[i programele cu pointeri este s\ desena]i ceea ce dori]i s\
programa]i, `nainte de a scrie programul.. Se folose[te creionul [i radiera. Vom vedea
cum.
Dac\ a]i r\spuns NU este cazul s\ citi]i povestea piciorului [i s\ deprinde]i o metod\ de a
`nv\]a rapid pe care n-a]i cunoscut-o. Dar mai `nt\i povestea piciorului, pe care v\ rog s-o
relua]i de c\te ori ave]i nevoie astfel ca s-o pute]i scrie cu cartea `nchis\. Nu tri[a]i!
Start!
Acum `nchide]i cartea [i scrie]i corect povestea piciorului ! De c=te ori a trebuit s-o citi]i
p=n\ s-o pute]i reproduce? De 4-5 ori? De mai multe ori?
De asemenea dificult\]i se lovesc to]i elevii care `nva]\ pe de rost, care buchisesc. ~n
realitate creierul nostru poate fi folosit altfel la `nv\]atul rapid dar probabil nimeni nu v-a spus
p=n\ acum acest lucru! Haide]i s\ citim iar\[i povestea piciorului, imagin=nd-o sau chiar
desen=nd-o! Desena]i-o dac\ vre]i chiar acum. Ceea ce ar trebui s\ v\ imagina]i [i/sau s\
desena]i am scris cu litere grase, `ntre paranteze. Desena]i !
Un dou\ picioare (un om) [ade pe un trei picioare (un taburet) [i m\n=nc\
un picior (un copan). Vine un patru picioare (un c=ine) [i smulge piciorul
(copanul) lui dou\ picioare (al omului). Sup\rat, dou\ picioare (omul) ia
pe trei picioare (taburetul) [i love[te cu el pe patru picioare (pe c=ine).
Patru picioare (c=inele) fuge `n trei picioare ([chiop\t=nd), cu piciorul (copanul furat) `n
din]i.
Iat\ deci scena pe care ar fi trebuit s\ v-o imagina]i de la `nceput, `n `ncercarea de a `nv\]a
povestea de mai sus. A[a-i c\ era o poveste u[or de `nv\]at, din prima citire? Nu uita]i c\ n-
a]i fi reu[it f\r\ a-i construi o reprezentare vizual\.
Iat\ deci povestea piciorului, a[a cum trebuia s\ v-o imagina]i de la `nceput:
«Un om [ade pe un taburet [i m\n=nc\ un copan . Vine un un c=ine [i smulge copanul
omului. Sup\rat, omul ia taburetul [i-l love[te cu el pe c=ine. C=inele fuge [chiop\t=nd, cu
copanul furat `n din]i.»
A[a-i c\ este mult mai clar\ ? Acum, dup\ ce am v\zut filmul ac]iunii, dup\ ce ne-am
Povestea piciorului (reprodus\ cu u[urin]\):
Un dou\ picioare [ade pe un trei picioare [i m\n=nc\ un picior. Vine un
patru picioare [i smulge piciorul lui dou\ picioare. Sup\rat, dou\ picioare ia
pe trei picioare [i love[te cu el pe patru picioare. Patru picioare fuge `n trei
picioare cu piciorul `n din]i.
Desena]i ! Un record sau obiect se deseneaz\ ca un dreptunghi vertical,
`mp\r]it cu linii orizontale `n mai multe zone, corespunz\toare fiecare unui
c=mp. Dac\ sunt doar dou\ c=mpuri pute]i desena recordul ca pe un
dreptunghi orizontal, `mp\r]it `n dou\ de o linie vertical\. La acele
componente care sunt pointeri pune]i un punct `n mijloc. Dac\ sunt pointeri NIL bara]i por]i-
unea, diagonal, din dreapta sus `n st=nga jos.
Pointerul `l desena]i ca pe o s\geat\ dreapt\ sau curb\ care pleac\ din punctul central al
c=mpului (sau variabilei) de tip pointer [i ajunge pe conturul obiectului (variabilei dinamice,
VAR L: MyLista;
Unde MyLista e tipul pointer la tipul record sau obiect declarat mai `nainte astfel prin dou\
declara]ii de tip, una pentru tipul pointer alta pentru record sau obiect:
TYPE
MyLista # POINTER TO MyElement;
MyElement # RECORD
Info : ….;
Urm : MyLista;
END;
Desenarea efectului lui NEW(p): Uita]i-v\ la tipul variabilei sau c=mpului p dat ca
argument lui NEW. Va fi cel mai probabil un tip record (sau obiect, rareori `ntreg, real sau alt
tip simplu). Dac\ e tip simplu desena]i un dreptunghi ca pentru orice variabil\. Dac\ este un
tip compus desena]i dreptunghiul corespunz\tor, `mp\r]it ca mai sus. Pentru componentele
pointer pune]i c\te un punct `n fiecare parte a dreptunghiului. Acum c\uta]i pe desen
variabila p sau c=mpul p . Acolo ar trebui s\ g\si]i un punct cu o s\geat\ sau un NIL (bar\
oblic\). {terge]i s\geata sau bara lui NIL, pune]i punctul dac\ lipse[te [i pornind de acolo
desena]i o s\geat\ p=n\ la dreptunghiul pe care l-a]i desenat mai `nainte.
Desenarea efectului unei atribuiri: Dac\ este vorba de o atribuire asupra informa]iilor [i v\
intereseaz\ s-o desena]i, scrie]i valoarea `n c=mpul corespunz\tor. La fel proceda]i [i pentru
variabile care nu-s de tip pointer.
Desenarea efectului unei atribuiri cu pointeri: Se [terge vechea s\geat\ sau bara lui NIL
[i se deseneaz\ noua s\geat\, indic=nd acolo unde arat\ membrul drept. O atribuire de
pointeri se deseneaz\ adesea practic ca o s\geat\ indic=nd spre destina]ia alteia. Excep]ie:
Dac\ membrul drept e nil, c=mpul din structur\ se bareaz\ cu bara oblic\. (vezi primele
figuri).
Exerci]iu de desen: Urm\toarele trei instruc]iuni, puse `ntr-o bucl\, adaug\ noi
elemente `n lista L.
Desena]i ce se `nt=mpl\ prin executarea repetat\ a instruc]iunilor:
Observa]ie (Oberon): ~n Oberon pute]i folosi direct “.” `n loc de combina]ia “^.” Deoarece
Oberon aplic\ automat operatorul ^ acolo unde lipse[te, pointerul poate fi folosit de
programator ca `ns\[i obiectul f\r\ s\ apar\ mesaje de eroare.
Nu uita]i: ~n Oberon pute]i folosi cu `ncredere pointerul ca [i cum el ar fi chiar obiectul sau
structura indicat\. Ba chiar se obi[nuie[te ca tipurile pointeri s\ aib\ denumiri care s\
sugereze clase de obiecte. Acum a]i `n]eles de ce tipul pointer `l numisem MyLista, `n
exemplul precedent !?!
R\spunsul la exerci]iu: Se adaug\ de fiecare dat\ c=te un nou element la list\. Dac\ este
primul, ultimul sau la mijloc v\ las s\ stabili]i desen=nd.
Dup\ acest antrenament la desen v\ pute]i `ncerca imagina]ia cu urm\toarele :
Ex2. Scrie]i programul pentru crearea unei liste de numere `ntregi la
care:
a) elementele se adaug\ la sf\r[it
b) elementele se adaug\ la `nceput
c) elementele se adaug\ la mijloc
Concluzia : Cum se pot implementa listele sau rela]iile dintre obiecte ? Folosind
c=mpuri pointer aflate `n structura RECORD-ului sau obiectului!
Exemplul «Serpa.prj»
Proiectantul unei aplica]ii orientate obiect sau a uneia `n care (m\car pe un nivel) se afl\ o
list\, are nevoie de o viziune mai larg\ asupra no]iunii de nivel (modul) dintr-o aplica]ie.
Dac\ p=n\ acum un nivel (modul) era o colec]ie de proceduri care ofereau servicii nivelelor
superioare din aplica]ie,acum situa]ia se complic\.
De la un nivel al aplica]iei putem cere:
- efectuarea anumitor servicii (proceduri obi[nuite)
- crearea de obiecte sau elemente din list\ (aceasta include [i inserarea lor
`n structura de list\, deci crearea leg\turilor, rela]iilor cu alte obiecte de pe
Pentru `nceput o descriere a jocului Snake care poate fi rezumat\ `n: Pe o tabl\ de joc
`mp\r]it\ `n p\trate se mi[c\ un [arpe (format dintr-o succesiune de segmente care ocup\
p\trate vecine) la fiecare mutare deplas\ndu-[i capul `ntr-un p\trat vecin. {arpele are ca
scop s\ ajung\ `n alt p\trat `n care `i apare hrana (pozi]ia ei se schimb\ pseudoaleator) [i
totodat\ de a se feri s\-[i mu[te coada sau s\ se loveasc\ cu capul de zidul `nconjur\tor.
Dar fiindc\ o imagine e mai gr\itoare dec\t o mie de cuvinte s\ d\m cuv=ntul imaginii.
Figura o gasi]i pe una din paginile urm\toare.
Deoarece OBERON este un limbaj pentru programare modular\, analistul echipei care
realizeaz\ proiectul opteaz\ pentru o ierarhie de trei nivele, trei module, dintre care:
1.Primul de sus con]ine jocul propriuzis. El se bazeaz\ pe serviciile oferite de al doilea nivel,
servicii care manipuleaz\ elementele sarpelui [i ocazional pe grafica oferit\ de cel de-al
treilea nivel.
2.Nivelul al doilea se ocup\ de lista de elemente care formeaz\ [arpele. El permite:
- Inserarea unui element `ntr-o lista (elementul va fi capul [arpelui, `n noua pozi]ie)
- {tergerea ultimului element dintr-o list\. Observati c\ `n lipsa dealoc\rii cu DISPOSE este
suficient ca pointerul din penultimul element (segment de [arpe) s\ capete valoarea NIL [i
astfel ultimul element se va pierde. (Fi]i f\r\ grij\, `l recupereaz\ colectorul de gunoaie -
Garbage collectorul.) Dac\ lucra]i `n C va trebui dealocat cu instruc]iunea explicit\: delete.
- Prelucrarea unei liste, parcurgerea unei liste, c\utarea `n list\ (pentru a vedea dac\
[arpele nu [i-a mu[cat coada sau dac\ viitoarea sa «hran\» `n loc s\ apar\ undeva pe tabla
de joc i-ar apare suprapus\ peste unul dintre propriile segmente.)
Toate procedurile de prelucrare a listelor s-a decis s\ fie recursive, bazate pe ideea c\ o
list\ este sau lista vid\ (sau lista de un element) sau un prim element de care se leag\ o
alt\ list\. Aceasta este o abordare clasic\ a prelucr\rii listelor.
Ca rezultat vom ob]ine o aplica]ie care func]ioneaz\ afi[=nd imaginea ca pe un text. Aici
segmentele [arpelui sunt afi[ate ca stelu]e iar hrana ca un fel de @.
A[a arat\ programul demonstrativ “Serpa.prj” `n func]iune, cu afi[aj realizat `n mod text.
~n fig.: A[a arat\ programul demonstrativ “Serpa.prj” `n func]iune, cu grafica color `n dou\ dimensiuni.
A doua imagine prezint\ ce se poate ob]ine atunci c=nd modulul destinat graficii este un
modul ce realizeaz\ grafic\ bidimensional\ color. Acest modul trebuie importat de modulele
care apeleaz\ la serviciile sale. Va fi suficient s\ importa]i / include]i modulul nou `n locul
celui vechi (`n dou\ locuri, `n cele dou\ module):
[i programul devine unul al c\rui efect se vede `n a doua imagine. Remarca]i cum simpla
schimbare a unui modul cu altul av=nd aceea[i interfa]\ [i capabil s\ realizeze mai bine
acelea[i lucruri schimb\ complet aspectul unei aplica]ii. De altfel exist\ o tendin]\ actual\ de
MODULE Segmente;
IMPORT Grafica:=Grafco; (* Deoarece apeleaza: Grafica.WriteCharXY(x,y," "); *)
TYPE
GrupSegmente* = POINTER TO Segment;
Segment* = RECORD
x,y : INTEGER;
urmator : GrupSegmente;
END;
E momentul s\ desena]i record-ul a[a cum este descris `n prima parte a capitolului, ca un
dreptunghi `mp\r]it `n trei por]iuni verticale.
Inserarea unui asemenea element `nc\ necreat `ntr-o list\ (`n fa]a ei) se face `n etape:
Aloc `nt=i memorie pentru element cu NEW, apoi completez c=mpurile structurii cu
informa]ii (x,y – pozi]ia segmentului pe tabl\). Tot acum se completeaz\ c=mpul pointer cu
valoarea care indic\ spre restul listei. Adic\ de fapt cu adresa vechiului cap al listei. Pentru a
fi evident [i pentru juc\tor efectul afisez pe tabla un simbol (*) `n pozi]ia dat\ de x,y.
Juc\torul va vedea capul [arpelui `n noua pozi]ie.
Aten]ie: Vechea variabil\ (Lista) care indica `nceputul listei va ar\ta acum spre noul
segment.
BEGIN
NEW(S); (* aloc memoria pentru segmentul nou,*)
S.x:=X; (* `i pun coordonatele *)
S.y:=Y;
S.urmator:=Lista; (* GrupSegmentele o urmeaza *)
Grafica.WriteCharXY(X,Y,"*"); (* apare grafic - poate lipsi*)
Lista:=S; (* lista incepe cu noul segment *)
END NouSegment;
{tergerea ultimului element din list\ presupune s\ parcurgem lista p=n\ `n locul `n care un
element din list\ (segment) nu mai are succesor, adic\ pointerul s\u indic\ nimic (NIL). Nu
uita]i c\ acel c=mp pointer este denumit «urm\tor». ~n general, prelucrarea recursiv\ a
unei liste `nseamn\ prelucrarea elementului curent urmat\ de prelucrarea restului
listei. Evident, testul dac\ s-a ajuns la sf=r[it e situat `naintea apelului recursiv care declan-
[eaz\ prelucrarea restului listei. Totu[i procedura de mai jos este pu]in atipic\, deoarece
testul obi[nuit dac\ o list\ s-a terminat se face verific\nd dac\ pointerul primit (capul listei)
este NIL sau nu.
(*{tergerea ultimului element din lista. Observa]i lipsa dealoc\rii cu DISPOSE *)
PROCEDURE LasaCoada* (VAR S:GrupSegmente);
BEGIN
IF S.urmator=NIL THEN
(* Pot sterge acest segment daca nu are succesor *)
Grafica.WriteCharXY(S.x,S.y, " ");
(* Iar pointerul din seg. anterior S, nu mai indica nimic *)
S:=NIL;
ELSE (* altfel il caut mai departe in restul listei *)
Prelucrarea tipic\ a unei liste se face astfel. Dac\ pointerul primit e NIL, lista e vid\ [i nu
am sau nu mai am ce prelucra. Altfel prelucrez elementul curent, acces=nd componentele
sale (c=mpurile) iar apoi prelucrez (dac\ mai este cazul) restul listei. De obicei mai este
cazul, excep]ie f\c=nd ni[te prelucr\ri la care prezen]a unui anumit element `n list\
determin\ oprirea prelucr\rii. Este cazul c\ut\rii `ntr-o list\, c\utare care se opre[te, evident,
`n momentul g\sirii elementului cerut.
~n jocul cu [arpele procedura care confirm\ sau infirm\ faptul c\ [arpele trece printr-un
p\trat anume (de coordonate x,y) este chiar o c\utare a pozi]iei date `n recordurile
elementelor adic\ de-a lungul [arpelui:
END Segmente.
Jocul propriuzis formeaz\ modulul principal al proiectului. A fost programat structurat, clasic.
Iat\-l, f\r\ alte comentarii.
END Serpa.
Modulul care realizeaz\ partea grafic\ a fost scris pe ideea compatibilit\]ii cu modulul
Display. El trebuie s\ ofere acelea[i servicii ca Display sau (dintre ele) macar pe cele cerute
de aplica]ia noastra.
MODULE Grafco;
IMPORT CP:=ColorPlane;
PROCEDURE Space;
BEGIN
CP.SetBackColor(0,255,0); CP.Bar(x1,y1,x2,y2,CP.ERASE);
END Space;
PROCEDURE Zid;
VAR
BEGIN
CP.SetBackColor(120,120,0);CP.Bar(x1,y1,x2,y2,CP.ERASE);
CP.SetForeColor(0,0,0);
CP.Line(x1,y1,x2,y1,CP.DRAW); (* sus*)
CP.Line(x1,y2,x2,y2,CP.DRAW); (* jos *)
CP.Line(x1,ym,x2,ym,CP.DRAW); (* mijloc *)
CP.Line(xt1,y1,xt1,ym,CP.DRAW); CP.Line(xt2,ym,xt2,y2,CP.DRAW);
END Zid;
PROCEDURE Segment;
VAR
BEGIN
CP.SetBackColor(0,255,0); CP.SetForeColor(0,0,0);
CP.Bar(x1,y1,x2,y2,CP.ERASE);
CP.Line(xt1,y1,x1,ym,CP.DRAW);
PROCEDURE Cireasa;
BEGIN
CP.SetBackColor(0,255,0);
CP.SetForeColor(255,0,0);
CP.Bar(x1,y1,x2,y2,CP.DRAW);
END Cireasa;
PROCEDURE WriteCharXY*(x,y:INTEGER;c:CHAR);
VAR
BEGIN
SetPoz(x,y);
CASE c OF
" " : Space; |
"#" : Zid; |
"*" : Segment |
"@" : Cireasa
ELSE ;
END;
END WriteCharXY;
PROCEDURE KeyPressed*():BOOLEAN;
BEGIN
RETURN CP.KeyPressed()
END KeyPressed;
BEGIN
CP.Open;
CP.SetBackColor(0,255,0);
CP.SetForeColor(0,0,0);
CP.Clear;
END Grafco.
Comentarii: Acest modul ofer\ servicii nivelurilor superioare prin aceste trei proceduri, care
`ntr-un limbaj din familia C-ului ar fi fost trei func]ii:
PROCEDURE WriteCharXY*(x,y:INTEGER;c:CHAR);
PROCEDURE KeyPressed*():BOOLEAN;
PROCEDURE ReadKey*():CHAR;
Ultimele dou\ au aceea[i semnifica]ie ca suratele lor din Display sau ColorPlane. Prima nu
este at=t de complet\ ca omoloaga sa din modulul Display. Aceast\ nou\ WriteChar [tie s\
afi[eze doar anumite caractere [i anume cele care ne interesau pe noi: # * @ [i spa]iul.
A[a cum a]i v\zut `n exemplul anterior, imediat dup\ crearea cu NEW obiectele au nevoie
de o ini]ializare. Obiectul nou creat este «tabula rasa», nu are informa]ii `n c=mpuri, nu are
nume de metode `n c=mpurile procedurale, nu are nici pointerii (care-l leag\ de alte obiecte)
ini]ializa]i. Iar uneori, «na[terea» sa trebuie acompaniat\ de «na[terea» altor obiecte care-i
sunt cumva subordonate sau trebuie s\ fie `n rela]ie cu el dar `nc\ nu exist\. ~n acest caz
acestea trebuiesc [i ele produse (cu new) [i ini]ializate.
La fel, la «moartea» obiectului ar trebui desf\cute anumite leg\turi ale lui cu alte obiecte.
Aceste leg\turi pot fi uneori `n dublu sens – ca la liste dublu `nl\n]uite - deci uneori presupun
[i modific\ri ale altor obiecte ce vor r\m=ne alocate. Chiar [i alte opera]ii suplimentare pot fi
necesare la «na[terea [i moartea» obiectelor: Afi[area de mesaje, `nregistrarea obiectelor
`ntr-o eviden]\, deschiderea sau `nchiderea unor fi[iere asociate, etc. Cum proced\m dat
fiind c\ sunt at=t de multe de f\cut la `nceputul [i la sf=r[itul existen]ei unui obiect?
Simplu, [tim deja cum! Grup\m toate aceste opera]ii `n c=te-o procedur\
(sau func]ie, `n C++). Una pentru «na[terea» alta pentru distrugerea
obiectului. Prima o ve]i apela imediat dup\ NEW(…), pe a doua imediat
`nainte de DISPOSE(…), dac\ limbajul nu permite apelarea lor automat\
(un limbaj care permite apelarea lor automat\ este C++). Ele se vor numi constructor
respectiv destructor [i au `n unele limbaje denumiri specifice. ~n Turbo Pascal se numesc,
prin tradi]ie, Init (constructorul) [i Done (destructorul). ~n limbajele orientate obiect
derivate din C (C^^, Java etc) constructorul poart\ numele clasei iar destructorul numele
clasei prefixat cu un simbol, cu semnifica]ia de nega]ie, de distrugere. Acest lucru este
justificat deoarece `n C^^, de exemplu, constructorul este automat apelat la declararea unei
variabile din acea clas\, prin `nse[i declararea ei. La fel, la ie[irea din bloc, din procedur\,
(vede]i no]iunea de domeniu de vizibilitate a variabilelor), c=nd variabila urmeaz\ s\ fie
dealocat\ C++ apeleaz\ automat destructorul. (Este foarte facil pentru programator dar
10
Tipuri şi tipizare; De la tipuri simple la tipuri
de obiecte polimorfe
Noţiuni: Tipuri, tipuri simple , tipuri conpuse, ARRAY, RECORD, POINTER, indexare,
selectare câmp, dereferenţiere, tipuri de date şi operaţii, compatibilitate de tipuri la atribuire, ...la
apel de proceduri şi returnare de valori, povestea clientului de la CEC, lumi de obiecte polimorfe,
tipul static şi tipul dinamic, ce sunt extensiile de tip, tipul dinamic şi pointerii sau referinţele,
exemplul cec.mod, clase derivate, metode suprascrise, (invocarea metodei clasei părinte),
instrucţiunea with şi alte teste de tip, calea spre extensibilitate.
Not\ despre mul]imi: Un caz aparte dar oarecum minor `n Oberon este tipul mul]ime
(SET), care `n Pascal era un tip compus. Prof. Wirth, creatorul Oberonului a p\strat doar
tipul mul]ime sub form\ de tip predefinit SET cu semnifica]ia de mul]ime de numere `ntregi.
(La urma urmei a[a ceva nu prea reduce generalitatea deoarece cu asemenea indici putem
indexa [i astfel putem alege un element dintr-u vector de orice fel de componente. Deci o
mul]ime de indici induce astfel o mul]ime de orice fel de elemente, de tip simplu, compus
sau – de ce nu – de obiecte). C\uta]i tipul SET `n documenta]ia electronic\ [i ve]i `n]elege [i
de ce Oberon nu mai folose[te acoladele pentru comentarii ca Pascalul. Da, a]i ghicit, cu ele
se noteaz\ mul]imile, exact ca `n matematic\. Cu mul]imi se fac opera]ii notate cu plus [i
minus (reuniunea [i diferen]a de mul]imi). Operatorul “apar]ine” se scrie cu majuscule: IN,
apartenen]a elementului x la mul]imea M scriindu-se evident: x IN M. {i alte limbaje au un
asemenea operator pentru a testa apartenen]a elementelor la liste sau mul]imi, cum este
operatorul 'elem' din Haskell.
Tipurile simple pe care le-a]i `nt=lnit [i de care v\ aminti]i cu siguran]\ (de altfel acestea
patru exist\ aproape `n orice limbaj modern) sunt `ntregii, realii, caracterele tipografice [i
valorile logice.
~n C aceste tipuri se numesc:
int - numerele `ntregi
float - numerele reale (`n simpl\ precizie)
char - simbolurile tipografice (de exemplu de pe tastatur\)
int - valorile logice TRUE [i FALSE sunt `n C `nlocuite de constantele 0 [i 1. ~n
esen]\ 1 `nseamn\ adev\r iar 0 fals.
Este de semnalat `n C [i prezen]a lui void, tipul care ]ine cumva loc de
mul]ime vid\. O procedur\ se va implementa `n C ca o func]ie care
returneaz\ un nimic, “elementul mul]imii vide” adic\ ceva din tipul void. De
re]inut aceast\ marc\ a procedurilor implementate ca func]ii `n C [i C++.
~n C++ principalele tipuri se numesc:
int - numerele `ntregi
float - numerele reale (`n simpl\ precizie)
char - simbolurile tipografice (de exemplu de pe tastatur\)
bool - un tip special nou introdus `n C++ pentru valorile logice TRUE [i FALSE.
Dar programatorii pot folosi [i folosesc `nc\ vechile conven]ii din C dup\ care adev\rul [i
falsul sunt `nlocuite,reprezentate de constantele (de tip int) 0 [i 1.
C=t despre opera]ii, unele sunt opera]ii interne pe mul]imea respectiv\
dar altele nu sunt, rezultatul fiind din alt\ mul]ime. ~mp\r]irea ( / ) a doi
`ntregi d\ un num\r real iar compararea (cu operatorii de compara]ie <, >,
>=,<=, = [i # adic\ diferit) a dou\ valori comparabile va da un rezultat
BOOLEAN, TRUE sau FALSE cu care apoi se pot face opera]ii logice ~ & OR. Aten]ie [i la
prioritatea operatorilor. Compara]iile sunt mai pu]in prioritare dec=t opera]iile logice
deci se vor scrie obligatoriu `ntre paranteze. Exemplu: o not\ este un num\r `ntreg n
astfel `nc=t (n>=1) & (n <= 10). {i fi]i siguri c\ doar a[a este corect `n Oberon! (~n C++ ar
fi fost: (n>=1) && (n <= 10)
Unele limbaje ofer\ [i tipuri numerice cu un interval mai mare de valori, cu mai multe
zecimale ([i care evident ocup\ pentru fiecare valoare mai mult\ memorie, adesea dublu.)
Oberon nu face excep]ie, lista tipurilor fiind dat\ `n documenta]ie (c\uta]i-o la Help ->
Compiler topics help):
Am citat din Help-ul care `nso]e[te Pow, preciz=nd pentru ne[tiutorii de englez\ c\
“between” `nseamn\ “`ntre” iar expresiile scrise cu majuscule ne dau valoarea minim\
(prima) [i maxim\ (ultima) pentru fiecare dintre tipuri. Dac\ `n loc de valori concrete folosi]i
aceste nota]ii atunci programul dumneavoastr\ va rula pe orice implementare de Oberon,
adapt=ndu-se tipurilor din acea implementare.
La r=ndul lor, limbajele din familia C-ului ofer\ ni[te modificatori de tip, cuvinte cheie cum ar
fi: unsigned, signed, short, long, double. Traducerea lor este imediat\. (Signed [i short sunt
desemantizate, prezen]a sau absen]a lor nu schimb\ nimic din reprezentare.) folosi]i `n
general ace[ti modificatori `n situa]iile `n care opera]i cu valori mai mari dec=t cele din tipul
uzual. (Exemplu: Dac\ folosi]i `ntregi pozitivi dincolo de 32768 [i p`n\ la 65535 opta]i pentru
unsigned int care se poate prescurta la unsigned. Dac\ utiliza]i `ntregi mult mai mari, cu
semn, cam p`n\ pe la dou\ miliarde pute]i folosi `ntregii pe 32 de bi]i: long int. Numerele
reale cu 5-6 zecimale exacte sunt float iar cele cu 10 zecimale exacte sunt double.)
Cum afl\ sistemul tipul unei expresii ? Compilatorul include un modul numit “type
checker” adic\ “verificator de tipuri” capabil s\ aplice asupra unei expresii reguli de tipul
“dac\ operanzii sunt de anume tipuri [i operatorul este cutare atunci rezultatul este de tipul
cutare (exemplu: `mp\r]irea a doi `ntregi folosind operatorul “/” d\ un rezultat real). Astfel,
din aproape `n aproape, sistemul afl\ la compilare tipul expresiei. Faptul c\ la aceast\
verificare se folosesc a[a-zisele “gramatici cu atribute” e un seceret [tiut doar de
constructorii de compilatoare.
Problema determin\rii tipului designatorului din st=nga atribuirii are o rezolvare mai
complex\ atunci c=nd e vorba de tipuri compuse. Reamintim c=te ceva despre ele:
~n Oberon putem defini tipuri compuse `n mai multe feluri. Descrierile de tipuri compuse pot
fi folosite direct pentru a declara variabile (se numesc tipuri anonime) sau pot primi un
nume (tipuri nominale) `n cadrul sec]iunii TYPE (sec]iune care poate exista at=t la nivel de
modul – tipuri globale modulului – c=t [i la nivel de procedur\ - [i atunci doar acolo, `n
procedur\, sunt valabile noile tipuri).
Atribuirile cu recorduri se fac prin proiec]ie. Valoarea unui variabile record cu mai multe
c=mpuri dec=t a altuia (vom vedea c\ se poate declara un asemenea tip extins) se poate
atribui unei variabile (designator) al unui record cu mai pu]ine c=mpuri. Evident c\ se
copie din record-ul mai amplu doar c=mpurile care `ncap, adic\ cele comune celor dou\
structuri.
Aten]ie: ~n Oberon dereferen]ierea este implicit\ dac\ urmeaz\ o selec]
ie, deci dac\ S e un pointer la record sau obiect pute]i folosi pe S ca [i
cum ar fi `nsu[i obiectul, av=nd acces cu S.<c=mp> la c=mpurile lui.
Cum afl\ sistemul tipul designatorului din st=nga atribuirii ? Dup\ declara]iile de tip. ~n
exemplul cu palatul califului, nota]iei (designatorului) p[salacrt].usa[nrusa] i se stabile[te
tipul astfel:
p – e de tipul Palat conform declara]iei variabilei p
p[salacrt] – e o component\ a tipului palat, care e vector (ARRAY ...
OF Camera) deci este de tipul Camera, un tip record.
Cu ocazia aceasta se verific\ [i tipul indicelui, care e corect
fiind `ntreg. (variabila salacrt era declarat\ de tip INTEGER).
p[salacrt].usa - are sens deoarece din tipul Camera, care e un record, se
alege o component\ numit\ “usa”. La r=ndul ei aceasta e un
vector (vede]i declara]iile din acel program) [i are sens s\ scriu:
p[salacrt].usa[nrusa] ... fiindc\ nru[\ are tipul `ntreg [i
este deci bun ca indice.
p[salacrt].usa[nrusa] - este din palat, dintr-o anume sal\, o u[\ din vectorul de u[i
anume cea cu num\rul nrusa [i are tipul tuturor elementelor
vectorului u[a, adic\ `ntreg deoarece a[a era declarat vectorul.
Defini]ie: ~n Oberon obiectele (recordurile) [i (printr-un fenomen de
inducere) pointerii au at=t un tip static c=t [i un tip dinamic. Tipul static
este tipul care apare `n declara]ie. ~l pute]i afla citind pur [i simplu
programul. Tipul dinamic este sau egal cu tipul static (ceea ce se `nt=mpl\
foarte des la record-uri [i obiecte nereprezentate prin pointeri) sau este o extensie a tipului
static.
Acesta din urm\ `n cazul c=nd lucr\m cu pointeri. (At=t tipurile extinse c=t [i pointerii la ele,
vom vedea c\ sunt compatibil la atribuire cu tipul de baz\ din care provin, pe care `l extind.
De altfel este evident c\ dac\ un record are mai multe c=mpuri ca altul valorile din el ne
ajung pentru a le atribui unui record care are doar o parte dintre aceste c=mpuri. La fel [i la
pointeri. Valoarea (adresa de fapt) care e un pointer ce indic\ o structur\ cu mai multe
c\mpuri poate fi atribuit\ unui pointer care indic\ o structur\ cu mai pu]ine c=mpuri – prima
parte din acele multe c=mpuri.)
Figura 1: Atribuirea dintre obiectul extins [i obiectul de baz\ (pointeri), desen preluat din lucrarea Object-Oriented Programming
in Oberon-2, de Hanspeter MÖSSENBÖCK, de pe site-ul Universit\]ii din Linz – citat anterior.
~n versiunea de Oberon cu care este livrat mediul Pow (Red Chili Oberon-
2 compiler) tipurile record sunt toate implicit extensibile ([i nu se cere
s\ preciz\m nimic pentru aceasta ca `n alte dialecte de Oberon). Ca
urmare putem defini un nou fel de tip record (sau obiect) indic=nd
doar ce au `n plus obiectele din noua clas\ (tip record) fa]\ de predecesoarele lor din
clasa p\rinte, acel tip record de la care mo[tenesc totul. Pe scurt, dac\ o clas\ de obiecte
pe care o am `n program este destul de bun\ pentru ceea ce vreau s\ fac dar mai are
nevoie de ceva `n plus (date sau comportamente exprimate prin metode) nu este nevoie s\
o scriu din nou, ci doar s\ indic tipul din care provine (clasa p\rinte sau – sinonim – tipul din
care deriveaz\, pe care `l extinde) [i s\ mai scriu doar ce are ea `n plus, c=mpuri de date
sau metode. Sintactic (`n Oberon) recordurile extensibile se scriu `n sec]iunea TYPE a
modulului sau a unei proceduri scriind dup\ cuv=ntul RECORD o parantez\ ce con]ine tipul
p\rinte, (tipul pe care `l extind, de la care mo[tenesc). Mo[tenirea multipl\ nu este posibil\ `n
Oberon. Deci:
E simplu de ]inut minte, dup\ RECORD scrie]i numele tipului p\rinte `ntr-o parantez\.
O nota]ie similar\ exist\ [i `n limbajul C++. Acolo clasele derivate au [i ele `n declara]ia lor
numele clasei din care au derivat dar numele nu este pus `ntr-o paranteza ci este precedat
de un ':' [i un cuv=nt care specific\ felul de mo[tenire (public, private sau protected).
Dac\ vreau s\ schimb un comportament (adic\ ceea ce face o metod\
existent\) ei bine, scriu noua metod\ (cu acela[i nume [i aceea[i
semn\tur\ adic\ schem\ de parametri) iar noua metod\ o va acoperi,
o va `nlocui pe cealalt\, `n noua clas\. E cam la fel ca la variabile globale
[i locale, unde o variabil\ local\ cu acela[i nume o acoperea pe cea global\ sau pe cea
Astfel noile clase de obiecte vor r\spunde la acelea[i cereri de a presta
servicii ca [i precedentele (serviciile, metodele, se solicit\ `n mod unitar
indiferent de tipul dinamic al obiectului) dar se vor comporta polimorfic,
f\c=nd ce li se cere dar `n diverse feluri. A[a c\ vom putea extinde un
enorm program deja existent dar f\r\ s\ schimb\m un r=nd `n el. Sun\ promi]\tor, nu-i a[a ?
(O tehnic\ modern\ de programare de acest fel – de care eu cel pu]in n-am auzit [i nici n-
am citit nimic `n publica]iile rom=ne[ti, tehnic\ cu care noile func]ionalit\]i sunt ad\ugate
treptat este “programming by difference” - programarea prin diferen]\). Revin la `ns\ ideea
extinderii:
Este nevoie doar s\-l punem pe program s\ prelucreze obiectele unei clase extinse, iar noile
func]ionalit\]i vor fi incluse `n metodele (suprascrise evident) ale noii clase de obiecte.
Programul r\m=ne la fel [i asemena func]ionarului de la CEC prime[te [i alte feluri de
documente (adic\ mesaje), eventual cu riscul de a nu [ti ce s\ fac\ cu ele. De altfel `ntr-un
mediu de obiecte care interac]ioneaz\ prin mesaje transmise prin difuzare (broadcasting)
adesea unele mesaje ajung [i la obiectele (“ascult\torii”) neaviza]i, care nu [tiu ce s\ fac\
recep]ion=ndu-le. Obiectele respective vor ignora aceste mesaje sau, dac\ sunt programate,
le vor trimite mai departe.
Totu[i acest lucru nu produce erori `n sistem iar obiectele [tiu s\ diferen]ieze mesajele
(cam ca func]ionarul de la CEC formularele) ceea ce fac de exemplu cu ajutorul instruc]iunii
WITH (Care WITH din Oberon nu seam\n\ deloc cu cel din Pascal). Ca idee, instruc]iu-
nea WITH este un fel de CASE pentru tipuri. CASE alegea ce avea de executat dup\
valoarea unei expresii. WITH alege ceea ce are de executat dup\ tipul dinamic al unei
variabile. Teoria mai spune c\ WITH trateaz\ acea variabil\, pe fiecare ramur\ respectiv, ca
[i cum ar fi chiar de tipul static depistat prin test. Iat-o, explicat\ pe scurt (`n documenta]ia
electronic\ exist\ o explica]ie succint\ dar mai tehnic\, folosind no]iunea de gard\ sau
gardian de tip - `n englez\ “type guard”, neexplicat\ `ns\ de noi aici):
Aten]ie: Ca de obicei acoladele nu fac parte din instruc]iune, sunt doar un mod de a marca
partea op]ional\ care poate apare de oric=te ori este nevoie (inclusiv niciodat\) iar
parantezele p\trate marcheaz\ partea op]ional\ care apare f\r\ repeti]ii (o dat\ sau
niciodat\). Egalul [i punctul final nu fac nici ele parte din instruc]iune ci sunt specifice
modului de descriera a sintaxei folosit.
Tipurile de date vor fi primele pe care le declar\m. Avem nevoie de dou\ tipuri derivate
Depunere [i Restituire. Ele con]in ambele Numele, Prenumele [i Num\rul de cont al
clientului plus un c=mp suplimentar, Suma depus\, pentru formularul de depunere [i
respectiv suma restituit\, pentru formularul de restituire. Componentele lor comune se
declar\ `n clasa (tipul) de la baza ierarhiei. Ambele tipuri derivate vor mo[teni aceste
Curio[ii vor g\si `n documenta]ia electronic\ ce `nso]e[te POW un modul OOPBase care
ofer\ de-a gata o clas\ de baz\ numai bun\ pentru a `ncepe o ierarhie de clase. Are chiar [i
metoda Init (constructorul obiectelor) declarat\, (o ve]i suprascrie `n clasele derivate)
precum [i alte facilit\]i. Acest modul poate fi importat de c\tre alte module `n care sunt
definite noi clase de obiecte. Astfel clasele de obiecte pot fi ad\ugate modul cu modul
extinz=nd aplica]ia. Nici clasa de la baza ierarhiei [i nici ProgMain-ul nu mai trebuie s\ fie `n
acela[i modul cu clasele derivate (cum este `n exemplul nostru din dorin]a de a nu-l r\sfira
pe trei-patru module). Profesioni[tii adaug\ clasele noi modul cu modul [i declar\ `n fiecare
asemenea modul c\ import\ modulul OOPBase. Alte medii de programare [i alte limbaje
pentru OOP ofer\ [i ele ceva asem\n\tor.
Foarte important [i util: Pointerii la tipul de la baza ierarhiei vor fi
compatibili cu pointerii la tipurile extinse, derivate. Practic ei pot ar\ta
orice fel de obiect, dup\ o atribuire ca cea din Figura1 (aflat\ cu circa 10
pagini `napoi). {i tocmai tipul acelui obiect va fi tipul lor dinamic!.
Practic dac\ vrem s\ indic\m un obiect oarecare declar\m o variabil\ pointer la tipul
de obiecte care este baza ierarhiei.
~n exemplul nostru cu CEC-ul pentru fiecare fel de formular declar at=t pointerul la tipul lui
c=t [i tipul record care-i descrie c=mpurile. Vor fi trei feluri de formulare, formularul generic
numit Formular, cel de Depunere (`l extinde pe Formular) [i cel de restituire (`l extinde tot pe
Formular). De fapt sunt pointeri [i iat\ un motiv `n plus s\ lucr\m cu pointeri `n Oberon:
Rela]ia de extindere `ntre tipurile record din Oberon este transferat\ [i la pointeri
astfel c\ tipurile pointeri corespunz\toare sunt tot extinderi unul altuia `n aceea[i
ordine. Iar cu operatorul «.» putem accesa at=t datele c=t [i metodele obiectului indicat de
pointer. Ceea ce face ca metodele ata[ate tipului record (proceduri legate la tip) s\ par\ c\
apar]in [i tipului pointer ce indic\ acele recorduri.
IMPORT D:=Display;
TYPE Formular=POINTER TO FormularT;
FormularT=RECORD
nume:ARRAY 10 OF CHAR;
prenume:ARRAY 10 OF CHAR;
nrcont:INTEGER;
END;
Am declarat tipul record de la baza ierarhiei(va deveni obiect c=nd `i vom scrie metodele).
Inten]ion\m s\ lucr\m cu pointeri la obiecte (`n locul obiectelor `nse[i) deoarece vrem s\
gener\m dinamic obiectele (pointerul va fi argumentul pentru NEW) [i vrem s\ beneficiem [i
de polimorfism.
La modul general, un formular oarecare va con]ine: nume, prenume, nrcont. Tipurile record
extinse le vom numi DepunereT [i RestituireT. Declar\m [i tipurile pointer aferente.
Depunere=POINTER TO DepunereT;
DepunereT=RECORD (FormularT);
SumaDepusa : INTEGER;
END;
Restituire=POINTER TO RestituireT;
RestituireT=RECORD (FormularT);
SumaRestituita : INTEGER;
END;
Tipul DepunereT `mpreun\ cu tipul RestituireT sunt extinderi ale tipului FormularT. Prin
urmare [i tipul Depunere c`t [i tipul Restituire sunt extinderi ale tipului Formular (rela]ia de
la recorduri se transmite la pointeri).
Sintactic vorbind, apelul metodei din clasa p\rinte se face scriind designatorul obiectului
(variabila obiect aici), punctul, numele metodei [i semnul c\ciuli]\ care indic\ faptul c\
metoda va fi cea de la clasa precedent\.
La cererea de a se afi[a a[a cum arat\, formularul de depunere va afi[a un titlu, va apela
metoda clasei p\rinte pentru a afi[a numele, prenumele [i nrcont apoi va afi[a informa]ia
despre depunere, valoarea sumei.
Deoarece va trebui s\ creeze cu NEW trei feluri de obiecte, acelor NEW-uri li se vor da ca
parametri trei feluri de pointeri, capabili a indica un FormularT, o DepunereT sau o
RestituireT. Utilizatorul va indica prin apasare pe o tasta (variabila tasta de tip CHAR) ce fel
de obiect dore[te s\ se returneze. Dac\ nu alege corect d sau r se va genera [i returna un
formular generic. Alegerea felului de formular ce se va genera o face procedura dup\
valoarea variabilei tasta. Fiind o alegere dup\ valoare se folose[te CASE.
BEGIN
D.WriteStr("Ce formular doriti ? d=Depunere, r=restituire = ");
D.ReadChar(tasta); D.WriteLn;
CASE tasta OF
"d" : NEW(foaie_de_depunere); RETURN foaie_de_depunere
| "r" : NEW(foaie_de_restituire); RETURN foaie_de_restituire;
Procedura IaUnFormular e deosebit\ de tot ce am `nt=lnit: Cele trei
RETURN-uri au ca argument c=te o dat\ de alt tip dar toate aceste tipuri
sunt pointeri la obiectele de pe o ierarhie de clase de obiecte (tipuri
extensibile `n fond) iar aceste obiecte pot fi indicate de un pointer la clasa
de baz\. Deci adresele celor trei obiecte sunt compatibile cu tipul rezultatului scris `n
antet, pointer la clasa de baz\, deoarece sunt extensii ale acestuia.Verifica]i recitind
declara]iile [i nu uita]i c\ rela]ia de extindere de la tipurile RECORD se transmite [i la
pointeri.
Ni[te preciz\ri tehnice pentru viitorii exper]i `n OOP: Procedura de prelucrare este de
fapt un «handler» , un manipulator de mesaje. (Considera]i acele formulare ca fiind exemple
de mesaje ce se pot transmite `ntr-un univers de obiecte). ~n teoria OOP-ului obiectele
din universul modelat care vor r\spunde la mesaje implementate prin asemenea
record-uri (sau obiecte – Da, mesajele ar putea fi ele `nsele obiecte ca [i `n exemplul
PROCEDURE ProgMain*;
VAR foaie:Formular; (* polimorfism *)
BEGIN
foaie:=IaUnFormular(); (* rezultaul are tip dinamic *)
foaie.Completare(); (* alegerea metodei e dinamica *)
foaie.AsaArata(); (* alegerea metodei e dinamica *)
Prelucrare(foaie); (* Prelucrarea se face diferentiat *)
(* E procedura "handler" de mesaje=foi *)
(* locul ei ar fi fost intr-un obiect *)
REPEAT UNTIL D.KeyPressed();
END ProgMain;
END Cec.
C=teva comentarii: Programul e unitar, alternativele, diferitele detalii ale celor dou\ feluri
de formulare sunt ascunse. Foaie va fi obiect polimorfic, tipul s\u dinamic (Depunere sau
Restituire sau Formular fiind determinat de alegerea clientului din metoda IaUnFormular).
Comportamentul formularului la Completare [i c=nd vrem s\ vedem c\ A[aArat\ depinde
de tipul dinamic al obiectului. Conform lui se apeleaz\ metoda clasei respective.
(Foaia de depunere va cere [i suma depus\, cea de restituire va cere [i suma restituit\ [i la
fel vor face [i la afi[are, afi[=nd [i suma depus\ respectiv cea restituit\).
Putem ad\uga oric=nd noi clase de obiecte, formularele noi cu care va lucra func]ionarul,
f\r\ a modifica programul principal. Tot ce e de scris sunt declara]iile claselor noi de
obiecte, comportamentul lor adic\ metodele (la noi Completare [i AsaArata). Dac\ ne oprim
11
Tipul BOOLEAN, expresii logice. Evaluarea
lor interactivă
Noţiuni: Tipul BOOLEAN (provenit din logică), Un nume celebru: G.Boole, Structurile în
care apare acest tip de date , Valori şi operaţii, Tabelele operaţiilor, Proprietăţi, Prioritate şi
paranteze, Sintaxa, regulile gramaticii expresiilor logice, Evaluarea «leneşului» - lazy evaluation,
avantaje şi dezavantaje, Interpretarea expresiilor logice – mod de a le evalua interactiv,
Implementarea interpretorului, Recursivitate mutuală, Folosirea tipurilor procedurale în locul
directivei FORWARD.
Este momentul s\ ne ocup\m mai aproape de un tip de date provenit din logic\, pe care l-
am `nt\lnit p=n\ acum ocazional, tipul BOOLEAN. R\spundem `n cele ce urmeaz\ la
`ntreb\rile: Unde `l `nt=lnim ? Cum sunt formate expresiile de acest tip – expresiile booleene
? Cum se evalueaz\ valoarea unei astfel de expresii ? (`ntr-un program [i respectiv
imperativ).
Ciudatul [i amuzantul (pentru unii) nume al acestui tip, care apare printre altele `n limbaje ca
Pascal, Oberon [i altele similare lor provine de la numele lui George Boole, matematician
[i logician englez, n\scut la 2 noiembrie 1815 `n Lincoln, Lincolnshire, Anglia [i decedat la
8 dec 1864. Din via]a acestui logician englez care a fost c\s\torit cu nepoata lui Sir George
Everest (da, cel al c\rui nume e dat celebrului munte!) merit\ s\ not\m c=teva date:
Autodidact `n matematic\ (`nv\]ase primele no]iuni de la tat\l s\u) George Boole a debutat
`n publica]iile de specialitate cu o serie de lucr\ri ap\rute `n Cambridge Mathematical
2) structurile repetitive din diverse limbaje, fie ele structuri cu test in]ial:
Nota bene: Bucla do ...while din C se execut\ c=t\ vreme condi]ia dat\ prin expresia <exp>
este nenul\, adic\ adev\rat\. (~n C zeroul `nsemna FALS). De asemenea este de remarcat
c\ `n limbajul C, instruc]iunea for poate avea a doua expresie, (expresia care determin\
oprirea buclei for) o expresie oarecare, fie c\ o consider\m boolean\ fie c\ o consider\m
`ntreag\.
Mul]imea valorilor tipului BOOLEAN este format\ din dou\ valori, TRUE [i FALSE. TRUE
`nseamn\ adev\rat iar FALSE `nseamn\ fals. Opera]iile sunt cele din logica matematic\. Nu
este absolut necesar s\ existe toate opera]iile din logic\ `ntr-un limbaj de programare,
- Disjunc]ia (sau): or || OR
- Conjunc]ia ([i): and && &
- Nega]ia (nu): not ! ~
Remarca]i c\ diversele limbaje nu au nota]ii unitare pentru opera]iile logice
deci la `nv\]area unui limbaj va trebui s\ `nv\]a]i separat pentru fiecare
limbaj denumirile acestor opera]ii. Aceste opera]i pot fi descrise prin tabele,
a[a cum adunarea era dat\ prin tabla adun\rii iar `nmul]irea prin tabla
`nmul]irii.
Am notat adev\rul, TRUE, cu 1 [i falsul, FALSE, cu zero. Nega]ia lui 1 (TRUE) este zero
(FALSE) iar nega]ia lui zero (FALSE) este 1 (TRUE). Aceste tabele pot servi la evaluarea
expresiilor logice exact cum tabelele adun\ri [i `nmul]irii servesc la calculul valorii expresiilor
aritmetice.
Aceste opera]ii au, de altfel, propriet\]i similare cu adunarea [i `nmul]irea. OR este ca un fel
de adunare iar & este un fel de `nmul]ire. Printre propriet\]ile analoage suratelor lor
aritmetice se num\r\ de exemplu distributivitatea lui & fa]\ de OR, exact ca distributivitatea
adun\rii fa]\ de `nmul]ire. Astfel pentru trei variabile booleene a,b, c declarate `n modul la
care suntem obi[nui]i:
Ultima expresie trebuie `n]eleas\ ca (c & a) OR (c & b) dar a fost scris\ f\r\ paranteze
deoarece, exact ca la aritmetic\ (unde `nmul]irea are prioritate mai mare ca a adun\rii) la
logic\ conjunc]ia (&) are prioritatea mai mare ca a disjunc]iei(OR). Nega]ia are cea mai
mare prioritate dintre toate cele trei opera]ii logice.
Alte opera]ii care pot produce ca rezultat o valoare bolean\, logic\, sunt compara]iile.
Prin compararea a dou\ valori dintr-un alt tip de date se ob]ine o valoare logic\. De exemplu
3 < 7 d\ TRUE iar 3 > 7 sau 3 = 7 dau ambele FALSE. C=nd sunt implicate variabile,
valoare expresiei booleene se calculeaz\ pornind de la valorile lor.
Aten]ie: Prioritatea acestor operatori de compara]ie este mai mic\ dec=t a oper-a]iilor
logice OR, &, ~ . ~n limbaje ca Oberon, Pascal, Delphi aceste compara]ii se vor scrie
obligatoriu `ntre paranteze. Exemplu: condi]ia ca un `ntreg n s\ fie o not\ din catalog se va
putea scrie a[a:
De[i teoria recomand\ s\ `nv\]a]i priorit\]ile tuturor operatorilor, de multe ori, atunci c=nd un
programator nu e sigur `n ce ordine se face calculul, el pune explicit parantezele necesare.
~n condi]ii de examen `ns\, un examinator poate sanc]iona un candidat printr-o not\ mic\
dac\ descoper\ c\ acesta nu cunoa[te teoria.
Comentariile din extrema dreapt\ nu fac parte din sintax\. Nota]ia este cea cunoscut\: Tot
ce e `n parantez\ acolad\ se poate repeta de oric=te ori (`n practic\, at=ta vreme c=t
urmeaz\ alt operator va urma [i un alt term). Bara vertical\ separ\ alternativele. Altfel ar fi
trebuit s\ scriem 5 reguli diferite pentru a explica cum e format un factor.
Preciz\m c\ vom `n]elege prin OperatorAdunare disjunc]ia (sau, OR).
Prin Operator~nmul]ire vom `n]elege conjunc]ia ([i, &) iar prin OperatorNega]ie vom `n]elege
nega]ia (~). Mai observ\m c\ la expresiile booleene nu exist\ ceva asem\n\tor minusului
sau plusului cu care `ncep uneori expresiile aritmetice.
~n Oberon, cuv=ntul “func]ie” folosit mai sus trebuie `n]eles ca apel al unei proceduri func
]ionale definite de utilizator sau ca apel al unei func]ii predefinite `n sistem.
Evaluarea unei expresii logice se poate face `n mod banal, exact ca evaluarea expresiilor
aritmetice. Opera]iile se fac `n ordinea priorit\]ilor, `ncep=nd cu cele mai prioritare [i cu cele
din parantezele interioare. (Practic dac\ descompunem expresia conform regulilor
gramaticale de mai sus – [i asta `nseamn\ practic s\-i facem analiza sintactic\ - ultimele
reguli aplicate vor corespunde opera]iilor care vor fi efectuate primele.)
Acest mod de evaluare presupune ca la `nt=lnirea unui operator binar (cu doi operanzi) s\
se calculeze valorile ambilor operanzi [i apoi s\ se efectueze opera-
]ia (conform tabelei). Se poate mai repede ? S\ vedem cum:
Am putea efectua calculele mai repede dac\, de exemplu, am [ti
rezultatul unei opera]ii `nainte de a calcula valoarea tuturor
operanzilor ! La expresiile aritmetice acest lucru nu era posibil. Acolo
suma, produsul, c=tul sau diferen]a a dou\ numere depindea efectiv de
ambele. La expresii logice se poate. S\ examin\m iar tabelele opera]iilor:
Avantaje:
1) Vitez\ mai mare la evaluarea expresiilor booleene.
2) Unele expresii «periculoase» `n sensul c\ pot produce nedetermin\ri nu mai dau erori la
execu]ie. De exemplu condi]ia (a # 0 ) & (x = 3 /a ) poate fi folosit\ [i testat\ f\r\
probleme chiar c=nd a are valoarea zero. Rezultatul va fi fals dar `mp\r]irea la zero nu va
provoca eroare de execu]ie deoarece algoritmul de lazzy-evaluation nu mai evalueaz\
paranteza a doua (al doilea operand al opera]iei & dintre un fals [i altceva nefiind necesar la
calcul). Dac\ `ns\ compilatorul nu implementeaz\ lazy-evaluation, expresia va da o eroare
la execu]ie, `n `ncercarea de a `mp\r]i pe 3 la zero.
Dezavantaje:
1) Lipsa evalu\rii unei p\r]i dintr-o expresie poate fi periculoas\ pentru
program, dac\ `n cursul evalu\rii por]iunii de expresie ignorate se mai
f\ceau [i alte opera]ii (`n principal de I/O dar nu numai).
C=nd este posibil ca odat\ cu evaluarea unei p\r]i de expresie s\ se fac\ [i
alte calcule ? Atunci c=nd acea parte de expresie este un apel de procedur\ func]
ional\, implementare a ceea ce numim func]ie cu efect-lateral (side efect).
Ce este o func]ie cu side-efect ? O func]ie care mai face [i alte opera]ii (modific\ri de
variabile, opera]ii de I/O, alte apeluri de proceduri care produc la r=ndul lor astfel de efecte)
`nafar\ de simplul calcul al valorilor returnate.
Caz banal: O func]ie care scrie [i pe ecran, `n scop de depanare, valoarea rezultat\.Dac\
func]ia este al doilea operand iar lazzy-evaluation nu o mai evalueaz\, efectul nu se mai
produce. (de exemplu nu se mai scriu pe ecran valorile ob]inute, chiar dac\ func]ia era
programat\ s\ fac\ a[a ceva).
n := f1(...) + f2(...)
sau n := f1(...) - f2(...)
b1 := f1(...);
b2 := f2(...); (* A doua func]ie va fi apelat\ obligatoriu acum!*)
b := b1 OR b2;
O situa]ie de acest fel vom `nt=lni mai departe, cu ocazia scrierii unui program care s\
evalueze interactiv expresii booleene, date de la tastatur\. Un asemenea program, numit
uneori interpretor alteori parser (deoarece parcurge expresia citind-o caracter cu caracter)
vom realiza `n continuare, pe baza regulilor din gramatica expresiilor logice, a[a cum este
dat\ mai sus.
Problema evalu\rii unei expresii logice dat\ `n mod interactiv este ceva mai rar `n practic\
(spre deosebire de evaluarea expresiilor aritmetice care ar fi de mai mare folos). Are `ns\
aplica]ii, fie c\ e vorba de scrierea unor interpretoare pentru limbajele de programare sau a
unor subrutine de[tepte pentru evaluarea solu]iilor date unui program de `nv\]are asistat\,
unul dintre acelea c\ruia s\-i po]i scrie `n fi[ierul cu `ntreb\ri [i r\spunsuri c\ solu]ia este
A&B&C&~D (adic\ A [i B [i C f\r\ D) sau de ce nu A&D|B&C (adic\ r\spunde corect cel
care indic\ m\car una din variantele A [i D sau B [i C. ~ntrebarea putea fi de exemplu “ce
tehnologii se pot folosi la realizarea unor anumite produse industriale” cu r\spuns corect
dac\ se indic\ m\car perechea A D sau m\car perechea B C.
A fost `ns\ propus\ la examene, teze, olimpiade [i concursuri, inclusiv la clase de liceu (dar
la olimpici). O variant\ a acestei probleme care presupunea evaluarea mai multor expresii
booleene exist\ `n arhiva cu probleme de pe site-ul Info Arena, versiunea de acolo fiind
semnat\ de Adrian Vladu. O reproducem `n continuare :
Boolean
“Haralambie a primit la scoal\ o tem\ destul de dificil\! El trebuie sa evalueze o expresie
logic\. Aceasta expresie con]ine variabile (litere mari ale alfabetului englez de la „A” la „Z”),
constante („TRUE” [i „FALSE”), paranteze rotunde („(” si „)”) [i operatorii logici „NOT”,
„AND” [i „OR”. „NOT” are prioritatea cea mai mare, „OR” are prioritatea cea mai mica. Ini]ial
toate variabilele au valoarea „FALSE”. Lui Haralambie `i place s\ evalueze expresii, dar
variabilele `[i mai schimb\ uneori valoarea [i expresia trebuie reevaluat\. Speriat din
aceast\ cauz\, a decis s\ apeleze la ajutorul vostru! ”
Problema cere s\ se evalueze ([i s\ se reevalueze) o expresie logic\ aprioric necunoascut\
pentru un set de valori ale unor variabile ce-[i schimb\ valorile.
Pentru simplitate vom presupune c\ expresiile sunt formate `n urm\torul mod, descris mai
pe scurt. Presupunem c\ au toate elementele, constante, variabile, operatori, paranteze,
formate dintr-un singur caracter, f\r\ alte spa]ii. O asemenea expresie se ob]ine imediat
(printr-o preprocesare) din expresia ini]ial\, dac\ expresia ini]ial\ nu se conforma
presupunerii. Conven]ia noastr\ de nota]ie pentru noile expresii va fi:
TRUE se va nota cu t
FALSE se va nota cu f
Variabilele se vor nota cu majuscule astfel c\ variabilele T [i F nu se vor confunda cu
constantele t [i f (TRUE [i FALSE).
Operatorii se vor nota astfel:
and se va transcrie &
or se va transcrie |
not se va transcrie !
Cu aceast\ conven]ie la fiecare citire a unui caracter din expresie citim `n `ntregime un
operand, operator sau o parantez\. Acest caracter, vom vedea, va fi stocat `ntr-o variabil\ [i
va servi la a afla ce regul\ a gramaticii s-a aplicat acolo. Dar s\ nu anticip\m.
Proiectul nostru (`n Oberon) va fi format din dou\ module, unul va fi interpretorul cel\lalt
programul care `l apeleaz\. Voi comenta interpretorul:
MODULE Intbool;
(* Evaluarea expresiilor booleene cu operatorii
& , | , ! , variabile majuscule si constantele t,f *)
IMPORT D:=Display,Strings;
CONST TAB=CHR(8);
Orice program de mari dimensiuni are o serie de proceduri care fac lucrurile de rutin\.
Citirea urm\toarei informa]ii, semnalarea erorilor, anumite teste des folosite sunt asemenea
exemple. Aceast\ prim\ serie de mici proceduri o ve]i copia de fiecare dat\ c=nd scrie]i un
interpretor. Am prefixat-o cu un comentariu vizibil:
(********************************************************************
Toate accesoriile
********************************************************************)
Dintre cele de mai sus sunt importante GetChar care aduce din sursa de date urm\torul
caracter de evaluat [i, mai important\, Match, care verific\ dac\ ceea ce a fost adus `n
variabila Look este ceea ce a[tepta el (adic\ Match) deoarece `l primise ca parametru.
Match compar\ parametrul s\u (care semnific\ ceea ce m\ astept s\ urmeze `ntr-o
expresie corect\) cu ceea ce vine efectiv `n variabila Look.
PROCEDURE IsAddop(c:CHAR):BOOLEAN;
BEGIN
RETURN (c="|")
END IsAddop;
PROCEDURE IsMulop(c:CHAR):BOOLEAN;
BEGIN
RETURN (c="&")
END IsMulop;
PROCEDURE IsNegop(c:CHAR):BOOLEAN;
VAR
BEGIN
RETURN (c="!")
PROCEDURE IsVar(c:CHAR):BOOLEAN;
BEGIN
RETURN (c>='A') & (c<='Z');
END IsVar;
PROCEDURE IsConst(c:CHAR):BOOLEAN;
BEGIN
RETURN (c='t') OR (c='f');
END IsConst;
Observa]i c\ testele verific\ dac\ ceea ce le e dat ca parametru este un operator similar
adun\rii (la noi disjunc]ia), unul similar `nmul]irii (la noi e conjunc]ia), unul pentru nega]ie, o
variabil\ sau o constant\. Pot fi modificate aceste teste func]ie de operatorii [i conven]iile
folosite `n scrierea expresiei. Aten]ie s\ nu apar\ confuzii, cazuri `n care dou\ teste diferite
dau simultan r\spunsuri pozitive. (dac\ TRUE ar fi fost T nu t am fi avut o confuzie de acest
fel).
Urmeaz\ parte acea mai important\ a interpretorului. O serie de proceduri care atunci c=nd
sunt apelate citesc o por]iune din expresie [i returneaz\ valoarea ei.
(*************************************************************
Proceduri care calculeaza valorile unor parti din expresie
*************************************************************)
(* Acestea avanseaza in expresie, fie folosind Match, daca
stiu ce va urma fie apeland direct GetChar *)
(* Daca se apeleaza insa alte proceduri cu numele Get...
atunci sarcina de a avansa cade in seama lor *)
Get Var, de mai sus, calculeaz\ valoarea unei variabile c\ut=nd acea valoare `n vectorul
Mem. Iar GetConst [tie c\ “t” va `nsemna TRUE iar “f” va `nsemna FALSE [i returneaz\
corespunz\tor acea valoare, dup\ cum variabila Look con]inea un “t” sau un “f”.
Urm\toarea procedur\ calculeaz\ valoarea unui factor. Factorul poate fi (vezi ultima
regul\ din gramatic\) o variabil\ - caz `n care valoarea sa o va afla GetVar, o constant\ -
caz `n care valoarea sa o va afla GetConst, un factor negat – caz `n care procedura factor
Procedura Term va calcula valoarea unui term care tocmai `ncepe.
Termul este un fel de produs (f&g&...), realizat dintr-o valoare a primului
s\u factor (aici apel\m procedura factor) c\ruia i se face “produsul”, pardon
opera]ia & cu eventualul factor urm\tor. Treaba aceasta mege at\ta vreme
c=t mai urmeaz\ al]i operatori “de `nmul]ire” cu aceea[i prioritate. Case-ul are doar acest
rost, de a selecta operatorii `n caz c\ sunt mai mul]i (dar nu e cazul la asemenea expresii
booleene) deci poate fi redus la textul marcat. Cum se g\se[te `n variabila Look un
Expresia este o “sum\” de termi a[a cum termul era un “produs” de
factori. Deci procedura care va calcula valoarea unei expresii va fi similar\
cu cea care calculeaz\ valoarea unui factor. Expresia are valoarea primului
term eventual dac\ urmeaz\ al]i operatori [i alti termi se face opera]ia
(disjunc]ia) `ntre valoarea veche [i cea nou\. {i tot a[a c\t\ vreme (while)
mai exist\ termi. Valoarea unui term care urmeaz\ se va calcula apel=nd procedura pentru
evalu\ri de termi, Term. Ea parcurge [i evalueaz\ termnul care urmeaz\. Dac\ ar fi fost mai
multe opera]ii similare ca prioritate, CASE-ul ar fi avut mai multe ramuri.
Pentru a avea valori (fie ele [i toate false) pentru variabilele de la A la Z din problem\,
vectorul Mem `n care ele sunt p\strate va trebui ini]ializat, fie [i cu FALSE peste tot.
PROCEDURE MemInit;
VAR i:INTEGER;
BEGIN
FOR i:= 0 TO ORD('Z')-ORD('A') DO
Mem[i]:=FALSE;
END;
END MemInit;
Astfel cele trei proceduri mutual recursive pot fi declarate f\r\ a se folosi ca `n Pascal
directiva FORWARD.
Modulul principal al proiectului nu face dec\t s\ exemplifice cum se foloseste evaluatorul.
~n principiu are de f\cut dou\ lucruri:
1) S\ ini]ializeze evaluatorul de expresii. Cu aceast\ ocazie se cite[te deja
primul caracter [i se ini]ializeaz\ variabila Look.
2) S\ apeleze procedura de evaluare a unei expresii, Expression.
Bine`n]eles, dac\ dori]i, pute]i scrie c=teva atribuiri `n plus `n program
pentru a schimba valorile unora dintre variabilele din vectorul Mem.
MODULE Evalbool;
IMPORT Display,Intbool;
Display.WriteLn;
Display.WriteStr("Dati expresia");
Display.WriteLn;
Intbool.Init;
IF Intbool.Expression() THEN Display.WriteStr("TRUE")
ELSE Display.WriteStr("FALSE")
END;
Display.WriteStr("Caracter neprelucrat:");
Display.WriteChar(Intbool.Look);
Display.WriteChar("'");
REPEAT UNTIL Display.KeyPressed();
END ProgMain;
END Evalbool.
Procedura Expression din modulul Intbool returneaz\ un TRUE sau un FALSE iar IF serve
[te doar la a alege ce afi[\m pe ecran `n fiecare din cazuri. Ultimul caracter introdus de
dumneavoastr\, dup\ ce se termin\ expresia, va aparea `precedat de mesajul "Caracter
neprelucrat:", dup\ valoarea expresiei.
Nota]i [i faptul c\ modulul Display nu con]ine proceduri specializate pentru afi[area valorilor
“ADEVARAT” [i “FALS” nici `n limba rom=n\ [i nici `n limba englez\. Dar deja v-a]i dat
probabil seama cum se putea scrie o asemenea procedur\ WriteBool folosind un if.
Realizarea proiectului
Faceţi implementarea ! Succes !
12
Fractali; Elemente de grafică folosind
modulul ColorPlane
Noţiuni: dimensiune geometrică, dimensiune fractală, autoasemănare, fractali, cel mai simplu
fractal, feriga matematică
De ce ne intereseaz\ fractalii?. ~nt=i pentru c\ sunt, dup\ cum a]i dedus deja, forme
fundamentale `n natur\. Apoi pentru c\ au aplica]ii. B\nui]i deja c\ dac\ li se cunoa[te
geometria [i propriet\]ile se poate da r\spuns la o serie `ntreag\ de probleme, altfel de loc
simple. ~ncep=nd cu estimarea cantit\]ilor de minereu ascunse `ntr-un volum cubic dat de
exploatare (a unui mineral `n carier\) [i termin=nd cu calculul masei lemnoase dintr-un
hectar de p\dure sau al volumului ploii care se va rev\rsa dintr-un cer par]ial acoperit de
nori. (At=t minereurile, filoanele c=t [i copacii din p\dure sau norii de pe cer sunt fractali !)
M\ crede]i ? R\u face]i ! Tocmai preg\team intrarea `n scen\ a unui obiect matematic, un
fractal bine`n]eles, a c\rui dimensiune nu este nici zero nici unu nici doi nici trei ci exact
logaritm `n baza trei din patru. Deci cam dimensiunea 1.261... Aproxim=nd-o cu o eroare
cam de 1% `i putem spune “1 [i un sfert”. Cum arat\ un asemenea obiect “unu [i un sfert “
dimensional ? ~l vom desena imediat `mpreun\, dar mai `nt\i procura]i-v\ o coal\ de h=rtie, o
rigl\, (ba chiar [i un compas – de[i el poate lipsi), un creion [i o radier\. Ultima este cea mai
important\.
Pornim de la un mare segment de dreapt\, desena]i-l orizontal [i numi]i-l AB. A este cap\tul
st=ng iar B este cap\tul drept. M\sura]i segmentul [i `mp\r]i]i-l cu dou\ puncte T1 [i T3 `n
trei p\r]i egale. T1 este mai aproape de A iar T3 mai aproape de B.
Aici un cunosc\tor de geometrie analitic\ ar observa c\:
t[1]. x :=(2 * a. x + b. x) / 3;
t[1]. y :=(2 * a. y + b. y) / 3;
t[3]. x :=(a. x + 2 * b. x) / 3;
t[3]. y :=(a. y + 2 * b. y) / 3;
Aici fiecare punct este v\zut de programator ca un record (`nregistrare) cu dou\ c=mpuri
numite x [i y, semnific\nd coordonata x respectiv y a acelui punct. Ve]i `ntreba acum unde
Procedeul se repet\ `n mod similar pentru toate segmentele AT1, T1T2, T2T3, T3B.
Pe r=nd, `nlocui]i AT1, T3B cu cele dou\ desene de mai sus. La fel pentru T1T2 [i T2T3, dar
`n cazul lor, mica figur\ va fi rotit\ cu v=rful spre st=nga, respectiv spre dreapta.
La pasul urm\tor s-ar ob]ine o figur\ ca `n schi]a urm\toare.
Aceasta este [i ideea. Considera]i c\ procesul continu\ similar ... la infinit. Ceea ce
ob]inem este fractalul din figura urm\toare:
Observa]i perfecta asem\nare a p\r]ilor cu originalul precum [i felul cum detaliile par a se
pierde la infinit. A]i dori o imagine mai mare, pentru a fi mai clar\ ? Inutil. Imaginea m\rit\
arat\, pe por]iuni, exact la fel cu originalul [i d\ o aceea[i senza]ie de neclaritate.
Care este dimensiunea unei asemenea figuri ? Vom `ncerca s\ ne ocup\m de por]iunea
AT1 a ei, care m\rit\ la scar\ de 3 ori reproduce figura `ntreag\. Dar aceast\ figur\ (curb\)
e format\ din 4 fractali, cei care se sprijin\ pe capetele AT1, T1T2, T2T3, T3B, deci este de
4 ori mai mare. ~n concluzie, dimensiunea acestei figuri este num\rul x cu proprietatea c\ 3
la puterea x este egal cu 4. De unde rezult\ c\ x este egal cu logaritmul `n baza 3 al lui 4 [i
este un num\r cuprins `ntre 1 [i 2.
Dori]i vede]i [i al]i fractali sau vre]i o dovad\ `n plus c\ forme din natur\ sunt fractali ?
Compila]i [i rula]i proiectul (scris `n Oberon) numit Fern, care e livrat `mpreun\ cu versiunea
pe 16 bi]i a mediului de programare Pow. ~l ve]i g\si `n directorul
c:\pow\examples\opal\fern dup\ instalarea mediului de programare pe discul c. Ve]i ob
]ine ca efect desenul unui fractal poreclit “feriga matematic\”.
S\ coment\m r=nd pe r=nd p\r]ile programului care a generat imaginea primului fractal
prezentat mai `nainte. Computerul va fi programat at=t s\ fac\ calculele cu numere reale c=t
[i s\ deseneze fractalul pe o suprafa]\ `mp\r]it\ `n pixeli – ecranul s\u. Imagina]i-v\ aceast\
suprafa]\ ca o coal\ de caiet de matematic\ av=nd circa 800 x 650 p\trate. Acesti pixeli au
coordonate `ntregi, sistemul coordonatelor fiind cu originea `n col]ul din st=nga jos al
ferestrei grafice. Modulul `ncepe prin a importa celelalte modulele necesare, Float – pentru
calcule cu numere reale [i ColorPlane – pentru grafica Color. Programul este o traducere [i
adaptare `n Oberon a unui program similar scris `n Pascal [i publicat `n revista IF 2/1991.
Iat\ [i declara]iile: o singur\ declara]ie de constant\ `n sec]iunea CONST (ele sunt de forma
<identificator> = <valoare>, separate prin punct [i virgul\), dou\ declara]ii de tip care
introduce tipurile Punct [i {ir (de puncte). Fiecare punct este o pereche de coordonate reale
x [i y. Variabilele a,b vor reperezenta punctele extreme ale segmentului.
CONST n=3;
TYPE Punct = RECORD x,y : REAL END;
Sir=ARRAY n+1 OF Punct;
VAR a,b:Punct ;
Procedura Plot are rolul de a desena pixelul de coordonate x, y pe ecran. Dar coordonatele
sunt reale (x,y :REAL) iar ecranul are pixeli cu coordonate `ntregi. Conversia se face
PROCEDURE Plot(a:Punct);
BEGIN
cp.Dot(SHORT(ENTIER(a.x)), SHORT(ENTIER(a.y)), cp.DRAW)
END Plot;
Procedura urm\toare verific\ dac\ distan]a `ntre dou\ capete succesive ale unui fractal
(fractalul ini]ial sau micii fractali care se vor desena pe treimile de segment) este mai mare
ca o constant\ epsilon, stabilit\ la un pixel. Evident c\ dac\ distan]a este mai mare ca 1
pixel mai avem `nc\ ce desena [i detaliile se disting pe ecran. La o distan]\ mai mic\ de un
pixel cu siguran]\ nu se vor distinge detaliile interioare segmentului AB.
Distan]a `ntre dou\ puncte se calculeaz\ cu teorema lui Pitagora. Este ipotenuza adic\
radical (se scrie Sqrt) din suma p\tratelor catetelor, (adic\ a produselor lor cu ele `nsele).
Care sunt lungimile catetelor ? Distan]ele dintre puncte pe axa Ox respectiv Oy adic\
diferen]ele dintre coordonatele x ale punctelor (respectiv coordonatele y).
PROCEDURE BigDist(a,b:Punct):BOOLEAN;
CONST eps=1;
BEGIN RETURN (eps < f.Sqrt((a.x-b.x)*(a.x-b.x)+(a.y-b.y)*(a.y-b.y)))
END BigDist;
Amuzament: Pute]i schimba simultan [i semnul factorului de scal\ din penultimul r=nd al
procedurii [i valoarea acestuia. ~ncerca]i cu «plus» [i 0.63 pentru a ob]ine o veritabil\ oper\
de art\ abstract\, evident, tot un fractal. Ce am ob]inut noi cu aceste valori vede]i pe pagina
al\turat\:
Cum se deseneaz\ asemenea figuri ? Cu o procedur\ recursiv\. Ideea
este c\ fractalul de la A la B este (dup\ ce calcul\m coordonatele
punctelor intermediare T1,T2,T3 cu procedura Puncte) format din
fractalul de la A la T1, urmat de punctul T1, apoi urmat de fractalul de la
T1 la T2, urmat de punctul T2, de fractalul de la T2 la T3 [i de punctul T3 [i `n final de
fractalul de la T3 la B [i de punctul B. Evident are rost s\ intr\m `n profunzimea detaliilor
doar dac\ distan]a AB este suficient de mare. Ceea ce explic\ testul f\cut cu instruc]iunea
IF.
#include <stdio.h>
void main(void)
{ char press_a_key;
cout << "Hello world !" << endl;
cin.get(press_a_key);
}
Mic program `n C++ cu obiecte c\rora li se cer servicii. Aici ni[te obiecte numite becuri c\rora li
se solicit\ ni[te servicii cu nume familiare: s\ se aprind\ [i s\ se sting\.
#include <iostream.h>
#include <stdio.h>
class bec
{ public:
int tensiune ;
int putere ;
/***************************************************/
void set_putere(int p) { putere=p;};
void set_tensiune(int t) {tensiune = t; };
// Aplicatia
Editarea codului [i compilarea unei aplica]ii cu Dev -C++ [i MingW C++ Compiler:
Editorul de proiect al mediului Dev C++ [i gestionarea claselor [i func]iilor din proiect.
Un simplu click pe func]ia sau clasa corespunz\toare v\ trimite `n acel fi[ier surs\ unde este ea
scris\ ! Pe monitoarele color func]iile /metodele sunt marcate cu un cub albastru iar variabilele /
c=mpurile cu un cub galben.
Un exemplu minimalist dar care ilustreaz\ modul de definire al operatorilor ce fac opera]ii cu
obiecte. Aici obiectele sunt numere complexe iar opera]ia este o adunare. Solu]iile elaborate
folosesc `ntotdeauna alocarea dinamic\ a obiectelor intermediare calculului [i dealocarea lor de
c\tre operatorul urm\tor. Observa]i c=t de natural se scrie programul principal – func]ia main().
#include <iostream.h>
class complex
{
private:
float real, imaginar;
public:
complex (int r=0, int i=1) {real=r; imaginar=i;}
complex& operator+(complex&);
void afiseaza_complex(void);
};
void complex::afiseaza_complex(void)
{ cout <<"\nComplex : " <<real <<"+i*"<<imaginar;
}
a.afiseaza_complex();
b.afiseaza_complex();
c.afiseaza_complex();
}
Chiar [i pentru o aplica]ie dintr-un singur fi[ier java trebuie s\ face]i [i fi[ier proiect (.prj) asociat.
Deoarece mediul Dev C++ poate fi folosit cu diverse versiuni de compilator [i acesta
poate fi instalat `n diverse directoare (exclud aici cazul favorabil c=nd a]i desc\rcat de
pe Internet un pachet complet con]in=nd [i IDE-ul [i compilatorul de C++) o mic\
“sincronizare” a lor este uneori necesar\ pentru ca IDE-ul s\ poat\ g\si rapid
compilatorul. Vizita]i [i la nevoie modifica]i op]iunile referitoare la directoare din meniul
Compiler Options. Asigura]i-v\ [i c\ locul bibliotecilor (directorul / folder-ul cu
biblioteci) este corect specificat..
class Camera
{ int nr;
char denumire[40];
char artefact[40];
int usa[4];
int bani;
public:
/* N-am constructor explicit; la vectorul de camere vom initializa
fiecare camera ulterior, cu metoda Init */
void Init(int, char *, char *, int, int,int,int,int );
void Play(int & salacrt);
};
Makkai Andras, Cecilia Cri[an, Kovács Sándor, Ghid de utilizare Turbo Pascal 5.0-5.5,
micro Informatica, Cluj-Napoca, 1991
F
***, Visual FoxPro 6.0 – Ghidul Programatorului, Teora, 2000 (p.16, 29-30,41-45 [.a.m.d)
Gamma, Erich: Helm, Richard; Johnson, Ralph;Vlissides, John: Design Patterns – {abloane
de proiectare – elemente de software reutilizabil orientat obiect, (trad. Radu Biri[) Editura
Teora, 2002
Jamsa Kriss & Klander Lars – Totul despre C [i C++ – Manual fundamental de programare
`n C [i C++,Teora 2004
Johanson A.-L, Eriksson-Granskog A., Edman,A.: Prolog versus you; Springer Verlag 1985
Kalisz Eugenia, Athanasiu Irina, Cristea Valentin, Ini]iere `n Turbo Pascal, Teora, 1995,
1998 etc.
Winfried Kassera, Volker Kassera, Turbo Pascal 6.0, Micro ATCI Tirgu Mures, 1992
Kovács Sándor , Turbo Pascal 6.0, Ghid de Utilizare, microInformatica, Cluj-Napoca 1992
Mu[lea Ionu]: Ini]iere `n C^^, Programare orientat\ pe obiecte; Ed. Micro Informatica, Cluj-
Napoca 1992
Mössenböck H. , Wirth N., "The Programming Language Oberon - 2", (p\r]ile incluse `n
Help-ul mediului de programare Pow.)
Pappas, Chris H. & Murray, William H.; Visual C++ : the Complete Reference, Osborne /
McGraw-Hill, Berkelley, California, SUA, 1998
Popa, Dan; Introducere `n Haskell 98 prin Exemple, Editura Edusoft, Bac\u, 2007
POW – Programmers Open Workbench & Red Chili Oberon 2 Compiler, Univ. Johannes
Keppler, Linz, http://www.fim.uni-linz.ac.at/pow/download.htm
Terry, P.D., Compilers and Compilers Generators – an introduction with C^^, International
Thomson, 1996, disponibil\ [i pe web `n edi]ia revizuit\ din 2000