You are on page 1of 96
& 3 a a a) i g 5 cs 3 oh Viad Hutanu Tudor Sorin ils pwr INFORMATICA INTENSIV (filiera teoreticd, profilul real, specializarea matematici-informaticd, intensiv informatica) Ciclul superior al liceului, clasa a XI-a Editura L&S Soft Bucuresti Copyright 2006 © Las SOFT Toate drepturile asupra acestet luerdri apartin editurli L&S SOFT. Cuprins Reproducerea integral sau partial a textului din aceasta carte este posibil& doar eu acordul in scris al editurii L&S SOFT. Manualul a fost aprobat prin Ordinul ministrului Educatiei i Cercetarii nt, 4446 din 19.08.2006 in urma evaluatii calitative organizate de catre Capitolul 1. Alocarea dinamic& a memoriei. i Consiliul National pentru Evaluarea gi Difuzarea Manualelor si este realizat in conformitate cu programa analitica aprobata prin Ordin al 1.1. Generalitat 4 13.02 2006. 12, Variable de tp pointer... : ministrului Educatiei si Cercetarii nr. 3252 din 13.02. 112.1 Viable dep pair in Basal 12.2, Vanable de tp porter in Gr Reforont!stingiil: 1, Abcare dnamies a merorel,. eta 2. acer aria Pc Prof. Dr, Victor Mitrana, Facultatea de Matematica, Universitatea Bucurest 1.3.2. Alocarea dinamicd in C++... Prof. grad I Valiana Patrigor, Colegiul National Bilingy George Cosbuc tibiae picpuse Raspunsut Tiparut executat la 8.0. LUMINATIPO er Str Luigi Galvani nr, 20 bis, sector 2, Bucuresti Capitolul 2. Liste liniare ...... a es 23 Anul parr: 2008 244, Defi fistelor Pree 23 22 Liste tniare alocate simp inlanflt. 24 ——$——_____ 222.1. Prezentare general... 2 Deserierea CIP a Bibliotecii Nationale n Romaniei 222.2. Crearea 3 afigarea isicior 4 2.23 Opera acura une sts | 28 HUTANU, VLAD 2.2.4 Aplicai ale lstelor linia... 34 Informaticd intensiv : manual pentru ciclul superior al toa2 come eee eres liceului : clasa a XI-a - (filiera teoretie’, profilul real, specializarea 22.43, Operali cu poinoame.... a. eater } matematici-informaticd, intensiv informatics) / Vlad Hujanu, Sorin 29. Laon este tl “39 n earea une iste Iniare aiocald dubia iia af Tudor. - Bucuresti : Editura L & S Soft, 2006 2.3.2, Addugarea unel inregistrari la dreapta....... 7 51 ISBN (10) 973-88037-0-5; ISBN (13) 978-973-88037-0-1 2.33. Adaugarea uneiinregistar a stanga.. TNs 2.3.4. Adéugarea uneiinregista in inter iste a) 1. Tudor, Sorin 2.36. Stergerea une! Ivegistal din interior iste vga 2.36, Stergerea une! inregistrari a stanga/dreapta lst 33 004075.35) 2.3.7. Listarea de ia stanga la creapta liste. {.004(075.35) 38, Listarea do la creapta fa stanga liste 2.4. Stiva implementata ca lst liniara simpiu Tnlanuit 25, Coada implementa ca ft iniaré simply ent Probleme propuse... 7 Raspunsur la testele gril. Editura L&S sort: & Adresa: Str. Stinjeneilor nr. 8, bl. 29, sc. A, et. 1, apt. 12, Sector 4, Bucuresti; Capitolul 3, Metoda Divide et Impera.........sccssseeee 3.1, Prezentare goneral8....ssess Telefon: 021-3321315; 021-6366344; 0722-530390; 0722-573701; BARE faloarea maxima dinr-un vector. Fax: 021-3321315; 3.2.2, Sortatea prin interclasar, E-mail: tsorin@Is-infomat.ro; 3.23. Sortarea rapida.. 3.2.4, Turnutile din Hanoi. Web Site: www.ls-infomat.ro. 3.2.5. Problema taieturior.. Cuprins de gratia... 3.3.1.1. Generalt (vatianta Pasca), 3.3.1.2. Generalitati (varianta C+), 2.8.1.8, Solarea culcrior gi procesul de desenare Pascal ieee) 8.3.2, Curba lui Koch pentru un triunghi echilateral 33.3, Cua lui Koch pentuun pa. 3.8.4. Arborele Probleme propuse RSpUNSUTi orn eree Capitolul 4, Metoda Backtracking, 43, rezetaren metodel a tcand se 412 Pani cre sia baza metodelboctracking. 414 Gimli immer meds tacky 411.4 Problema elon dame 42. Mal pine nin progremul sure 43 Cant meare se core osrgu sce. Eerie probleme colori Nie. 48. Aptcai sie metodo backtracking n combinatca. a. generalize itl oS 442. Proeuscaterian ; 443. Gonare at sir na rie 44.4 Generaoa combnor : 445, Generarea aranementelo 448, Gonorarea tutor partior mali (2,2 45; Aa pin proba cre exo pr lzaeamatloel aciecing. 114 154. Conor. ee 4152. Generaroa patos wel numa naturel 4150, Pteta uno sumo ou banonte dolor data. 4, Proboma bit 458 Problema bio 456, Sania cali Probleme propuse. Indica Capitolul 5. Metoda Greedy ...... 5.1, Generalitati. 15.2. Probleme peniru care matoda Greedy conduce ia sotaia orien. 5.2.1, Suma maxim’. 52.2, Problema planifcari spectacolelor... 5.2.3, Problema rucsaculul (cazul continu)... 5.2.4. 0 problema de maxim... 5.8. Greedy eurist, 5.8.1. Plata unei st 5.8.2 Séritura calull....... a tl 5.3.3, Problema comis-voiajouli. eee Probleme propuse 7 Raspunsuri / Indica Manual de Informatic’ pentru clasa a XI-a 5 Capitolul 6, Programare dinamica ...... 145 6.1. Generali . en cece ctesstct ens AB: 6.2. Problema trlunghiulul, 6.3. Subsir cresc&tor de lungime maxima... 64. 0 problema cu sume, 6.5. Problema rucsacului (cat 6.6, Distanfa Levenshtein.....0.0 6.7. Ineruitrea optima a unui gir de matrice. 6.8. Probleme cu orcinea lexicografics @ permutarilor. 174 6.9. Numérul pattitilor unei muitimi cu n elemente.. 17 Probleme propuse. i a 180 Indicati i F 183 Capitolul 7. Grafuri neorientate ... 7.4. Introducere 72. Defiita gr 7.4, Graf complet. 7.8. Graf partial, subgraf. 7.8, Parcurgerea grafurior neoreta.. 78, Graf conax. 7.9. Componente conexe. 7.0. Cietur . 7.11. Cicks eulerian, graf euierian.. 7.12, Grafurl bipartite... 7.18. Grafuri hemiltoniene. Capitolul 8. Grafuri orientate ........ 8.1, Noflunea de graf orientat...,. 8.2. Memorarea graturior orientate 8.3, Graf partial, subgra........ 8.4, Parcurgarea grafurlior. Drumur, Circuito, 8.5. Graf complet si graf tumeu. 8.6. Graf tare conax. Componente tare conexe. 8.7, Drumuri de cost mintth.c.rnu fs 8.7.1. Introducere.... 8.7.2. Algorimul Roy-Floya.. 8.7.3. Utlizarea algoritmul Roy. Floyd pont Programul va utiliza atéta memorie cat are nevoie. Nu intotdeauna se poate cunoagte, de la inceput, de cat memorie are nevoie, aceasta se decide in timput executari, in functie de datele de intrare. In plus, daca o variabilé nu mai este necosara, exist& posibilitatea sa eliberam memoria ocupata de aceasta. O astfel de abordare conduce ia micgorarea substantial a necesarului de memorie a unui program. Capitolul 1, Alocarea dinamic’ a memoriei in varianta Borland a limbajelor Pascal gi C++, memoria din segmentul de date nu este intotdeauna suficient’, ea este limitata la 64K. Apoldnd la Heap, se mareste memoria disponibila. Anumite structuri de date, pe care le vom studia in am@nunt, se implementeazé cu usurinté in Heap. Un exemplu In acest sens sunt listele liniare, dar acestea sunt prezentate in capitolul urmaitor. 1.2. Variabile de tip pointer 1.2.1, Variabile de tip pointer in Pascal ‘Am ‘nvitat faptul c& memoria interna poate fi privita ca o succesiune de octetl, Pentru ai distinge, acestia sunt numerotati. Definifia 1.3. Numarul de ordine al unui octet se numoste adresa lui. Orice variabila ocupa un numar de octeti succesivi. De exemplu, 0 variabita de tip integer ooupa doi octefi, variabitel, RB Definitia 1.4. Adresa primului octet al variabilei se numeste adresa Observatie. Nu trebuie confundats adresa unei variabile cu valoarea pe care aceasta 0 memoreazal Memorarea adreselor variabilelor se face cu ajutorul variabilelor de tip pointer. = Variabilele de tip pointer se caracterizeaza prin faptul c& valorile pe care le pot memora sunt adrese ale altor variabile. Ele nu pot fi citite, nu pot fi tiparite in mod direct gi, cu 0 exceptie, continutul lor nu poate fi modificat in uma unor operatii aritmetice (de exemplu, nu puter incrementa o asttel de variabild), Limbajul Pascal face distinetie intre natura adreselor care pot fi memorate. Asttel, exist adrese ale variabilelor de tip integer (formand un tip identificat prin sintagma uzuala "pointer cétre variablle de tip integez”), adrese ale variabilelor de tip real (‘pointer catre variabile de tip rea"), adrese ale varlabilelor de tip string ("pointer cétre variabile de tip sting”). Din acest motiy, tipul pointer esto variat. 1 Tn ultimele versiuni ale celor dou jimbaje, memoria din segmentul de date nu mai este limitat&, ci se poate folosi Intreaga memorie disponibila. Din acest punct de vedere, daca se folosesc aceste versiuni, avantajul "memoriel in plus* nu mai poate fi luat in considerare. Manual de informatica’ pentru clasa a Xi-a 9 > && Tipul unei stfel de variabile pointer se declaré ca mal jos: type nune=*tip. 1, Veriabile de tip pointer catre variabile de tip integer. Varlabilele agri, aax2, pot refine adrese ale vatiabilelor de tip intreg. type adr_ints*integer) var adrl,adr2:adz_int) numariinteger) Foc ® Variable de tp pointer catte variable de tip reat. Variable adrewa, b v poate refine adrese ale variabilelor de tip real. type adi : var adzeaa: adz_real; _ 3. Variablle de tip pointer catre variabile de tip inreg. Tipul inzeg este tip record. Variabila adr_inz, poate retine adrese ale variabllelor de tipul inreg. type inregerecord pune rstring[10]7 prenune:string{10]; varata:byte; end; type adr_inregs*inreg: var adr_inrtadr_inreg Observatii intre variabilele de tip pointer sunt permise atribuiri doar tn cazul in care au acelagi tip pointer (retin adrese catre acelagi tip de variabile).. Exemplu: adri, adr2:Sinteger; adr3! *real: Atribuirea adri:=adea este corect4, iar atribuirea adr3:=ade2 nu este coracta. Chiar gi in cazul in care avem tipurile identice, dar descrise diferit, atribuirea nu este posibild. Atribuirea din exemplul de mai jos este eronat, Exemplu: type adrosentintegers var adeliadzese; adraisinteger; adr2inadedy 10 Capitolul 1, Alocarea dinamicé a memoriei Pentru a obfine adresa unei variabile oarecare se foloseste operatorul “a” prefixat. Adresa va fi memorata de o variabii’ pointer catre tipul variabilel a cael adresd a fost returnata de operatorul “e", Pomind de la o variabil& de tip pointer care memoreazi adresa unei variabile, cu alutorul operatorului “*", posttixat, se poate adresa continutul Variabitei a cérei adresd este memoratd. 1. in programul urmator, variabilel x, care este de tip intege: airibule valoarea 3. Variabilei a, de tip pointer catro integer, i se atribule adresa lul x. Pornind de la continutul variabilei a, se afiseaza continutul variabil type adrint=*integer; var a:adzint xtintegers begin t=) arndac; weiteln(a*); ena. 2, in programul urmator, variabilei v, de tip tnxeg, | se atribuie o valoare. Variebilei adresa, de tip pointer catre tnzeg, ise atribuie adresa lui v. Pornind de fa continutul variabi . 8@ afigeaza continutul variabilei v. type adrinreg="inreg; Enregerecord numeratcings varsta:integers end; need? adresa:adrinreg; weiteln(adresa*.nune,' ', adresa*.varsta); ond, Manual de informatica pentru clasa a Xl-a u 1.2.2. Variabile de tip pointer in C++ ‘Am Invatat faptul c& memoria intema poate fi privita cao succesiune de octeti, Pentru 2-idistinge, acestia sunt numerotati Dofinifia 1.3. Numarul de ordine al unui octet se numeste adresa lui. x rice variabila ocups un numar de octefi succesivi. De exemplu, 0 Variabilé de tip Ant ocupa doi octefi (in varianta Bortand C++ 3.0). GS Definitia 1.4. Adresa primului octet al variabilel se numeste adresa variable f Observatit ¥ —Nutrebuie confundats adresa unel variable cu veloarea pe care aceasta 0 memoreazai Y-Uneori in Jo do adresa a unel variable vor folos termenul pointer! Memorarea adreselor variabilelor se face ou ajutorul variabilelor de tip pointer. = Variabilele de tip pointer se caracterizeaza prin taptul c& valorile pe care le pot memora sunt adrese ale altor variabile, Limbajul C++ face distincffe intre natura adreselor care pot fi memorate. Astfel, exist adrese ale variabilelor de tip int, adrese ale variabilelor de tip float, adrese ale variabilelor de tip chax, eto. Din acest motiv si tipul variabilelor de tip pointer este diferit. = Tipul unei variabile de tip pointer se declar’ ca mai jos: tip *nune. 1. Variabile de tip pointer c&tre variabile de tip int. Variabilele adr gi ‘ade2 pot retine adrese ale variabilelor de tip int. Privii declaratia de mai jos: dnt tadri, *adr2; 2. Variabile de tip pointer catre variabile de tip £1oat. Variabila adresa, poate refine adrese ale variabllelor de tip Eeat: float* adress; 2 Capitolul 1, Alocarea dinamic& a memorlei 2) 3 Variabite de tip pointer catre variabile de tip eLev, care la réndul for Exc: suntde tip weruet. Variable a gi b, pot retin adrese ale variabillor de tipul etev. struct elev {char mune [201, prenuna[201; float nota_nate, nota_infor int varstar ” elev “a,b; L Obsorvatii Y — Caracterul “s* poate fi agezat in mai multe feluri, dupa cum se observa: Ant* adety int * adriy int tadri ¥ Pentru a declara mai multe variabile de acest tip, caracterul "*" se trece de fiecare data: 7 int *adri, ‘adr2, *adr3; Y — Odeclatatie de genul "int* ade1, ade2y" are semnificatia cA adr este de tip pointer cétre ane, in vreme ce adr2 este de tip int. Atentle! Aici se greseste deseor => Adresa unei variabile se obfine cu ajutorul operatorutul de referentlere “e", care trebuie s& preceada numeie variabilei: aNume_variabilay adrisknumar; - variabilei adr | se atribuie adresa variabilei numar. Ex: = Fiind dat& o vatiabilé de tip pointer catre variablle de un anume tip, care memoreaz’ o adresa a unei variabile de acel tip, pentru a obfine continutut variabilei a cérei adres& este memoratd, se utlizeaz’ operatorul unar “*", ‘numit gi operator de dereferengiere. 1. Variabila a este initializata cu 7, lar variabila eax este initilizaté cu adresa lui a. Secvenfa afigeazé confinutul variabilei a (7), pornind de la adresa ol, retinutd de ade: Ant ae7, tadrecay cout<". Acesta accoseazé un camp al unei structuri pornind de la un pointer (adresa) catre acea structura. El are prioritatea maxima - vezi tabelul operatorilor. Tipdrirea se poate face si aga: cout <prenune; ‘inte variabile de tip pointer sunt permise atribuiri doar in cazul in care au ‘acelagi tip pointer (retin adrese c&tre acelasi tip de variable). Exemplu: int *adri, raara) float vadr3; 77 Anivializart Atibulrea “adrisadr2" este corecta, iar atribuirea ‘adr3=adx2" nu este corecta. In aceste condi, va puteti intreba: cum putem atribui continutul unei variabile de tip pointer catre tipul x, altel variabile de tip pointer c&tre tipul y? in definitiv, amandoua retin 0 adresé... in acest caz, se utilizeazé operatorul de conversie explicita. De aceasta dat’, pentru exemplul anterior, atribulrea: *ady3=(£loat*)ade?" este corect’, 14 Capitolul 1, Alocarea dinamica a memorlei 1,3. Alocarea dinamica a memoriel 1.3.1. Alocarea dinamica in Pascal ‘Anumite variabile pot fi alocate dinamic. Asta inseamna &: > — Spatiul necesar memorarit este rezervat Intr-un segment special destinat acestui scop, Numit HEAP. > Rezervarea spatiului se face in timpul executéri programului, atunci cand se ‘execut’ 0 anumit’ procedurd, sorisé special in acest Scop. > Alunci cénd variabila respectiva nu mai este uti, spatiul din memoria este eliberat, pentru a fi rezervat, daca este cazul, pentru alte variabile. jin Bortana Pascal, pentru alocarea dinamica se utilizeazé urmatoarele ov’ proceduri: -— Procedura New alocé spatiu in HERP pentru o variabila dinamic’. Dupa ‘alocare, adresa variabilei se gaseste in P'. procedure Wew(var Pi Pointer) -— Procedura Dispose elbereazé spatiul rezorvat pentru variabila a caret adres este refinuté in p. Dupa eliderare, confinutul variabilei P este nedefinit. procedure Diapose(ver P: Pointer) Mecanismul alocarii dinamice este urmatorul: «Se declara o variabilé pointer, s-o numim B, care permite remorares unel adrese. «© Ge loc’ variabila dinamica prin procedura New, de parametru P. in Umma alocéril, variabila P retine adresa variabilel alocaté dinamic. © rice acces Ia variabila alocata dinamic se face prin Intermediut variabitel P. p segment de date Figura 4.2. Accesut la varabla alocat® dinamo 7 pack au exietd spaiu in MEAP, P rtine mi (rii o valoare). In practic, tntotdeauna se face tostit cenenje!spayuiui_Dn motve didactie, pent a nv cempea programete n exerplels pe cere le vom ‘da nu vor fest existenfa spatilul In HEAP. Manual de informatica pentru clasa a Xl-a 15 = — Pentru a elibera spatiul ocupat de o variabila di ti inamica, @ cdrel adres’ se GAseste th P, se uilizeazd Dispose, de parametru P. Dupa eliberarea spatiului rezervat pentru vatiabila data, conjinutul variabilei p este nedatinit. > Flind data o variabité de tip pointer catre varlabite d t fe un anumit tip, pentru a aeosea cont variable! cate) adresé este momorats, 0 tizears ‘numele variabilei de tip pointer urmat de operatorul "*", 1. Variabile de tip pointer catre variabile de tip integer. Variabilole adr. si adr2 pot refine adrese ale variabilelor de tip intreg, type adr_int="integer; var adriiadr_ints {eau adri: integer prin renuntaroa 1a prima linie} Roviedst) (aloe apatin in MEAP pontmu o vartabite shoe op ite de tio aarttie7) arishlia retine 7) Weltoin(ader) { Elparose continitul acostel variabite dispose(adr) {eliberez spatiul) eriapiie (>) 2, 2. Vertiabile de tip pointer catre varabile de ti ip real, Variabila adress, GE: Fema ene arese de varehierdeip reste ne Mares type adr_real=*reals var adreaa: adr_real; new(adresa) + adresa’1=7.65; writeln(adresa’s412)7 3. bare de tip pointer catre variabile de tip inreg, care la randul lor, sunt de tip xecord. Variabila adr_ine, i 2 variabilelor de tipu! inreg. Ser Peres erate eet type inregerecord ume :stzing{10] 7 prenume:string{10]; varsta:byte; end; adr_inrege*inreg; var adviade_inxeg: begin Feadln(adr*.nune) ; roadin(adr*.prenune) ; roadin(adr*.varsta) ; writen (ade* mune); writeln(adr*.prenume) ; writeln(adr*.varsta); Capitolul 1. Alocarea dinamici a memorie! 4, Programul urmator citeste gi afigeazé o matrice. Nou este faptul oa matricea este alocata in HEAP. type matricosarray[1..10,1..10]of integer; adr_mat=*matrice; var adciadr_mat) myn, i, jrintegers begin weite('me') ;readin (a); write('ns') ;readin(n); new(adr) 7 for itsl to m do for Jr=1 to n do readin(ade*{4,31)7 for ital to m do begin for J:sl ton do write(adrs{i,j}14)7 weiteln; ena; ena, 5, Este cunosout faptul o& functile nu pot Intoarce decat tipuri simple. Prin turmare, 0 functie nu poate intoarce o matrice care este descrisé de un tip structurat, Dar tipul pointer este simplu. Aceasta inseamna ca o functie poate intoarce un pointer. in cazul in care avem un pointer catre 0 matrices (retinuts in mear) se poate spune, prin abuz de limbaj, c& 0 tunctie intoarce 0 matrice. Programul urmator citeste doud matrice si afigeaze ‘suma ior. Matricele sunt rezervate Tn HEAP. type matricesarray[1,.10,1,.10]of integer; adr_mate‘natrice; var adrt,ade2,adz3:adz_mat; myn:integer; function cit_Mat (m,n:integer) iadr_mat; var i,jrintegex; adrradr_nat) begin new (adx) ; for diel to m do for Jre1 to n do roadin(adrs{i,J3)7 cit_Matieadry endy function Suma Mat (adri, ade2rade mat) :adz_mat; var i, jrinteger; aderadr_mat; begin new (ade) 7 for Lil to m do for Ji=l to n do ade*{i,S]smaded*{i,j]+ade2*(i,d17 Suna_Matreadr) end; Manual de informatic& pentru clasaaXI-a___ v7 procedure Tip_Mat (ade:adr_mat); var i,j:integers begin for i:e1 to m do begin for Jj writeln; end end; begin write (‘ms'); readin(m); write('ns')) readinin); aGrir=Cit_Mac (myn); adx2:=< aGr31=suma Mat (adei, ade2) ; ‘Tip_Met (adz3) ; end. ton do write(ade*{i,j1:4); 1.3.2. Alocarea dinamica in C++ In c++, pentru alocarea dinamicd se utiizeaz’ urmatorll operator: = Operatorul mew alocé spatiu in REAP pentru o variabiki dinamica. Dupa alocare, adresa variabilel se atribuie lui #, unde P este o variabilé de tip pointer catre tip’: Penew tip. Observatil Numérul de octeti alocati in HEAP este, evident, egal cu numérul de octeti ccupat de o variabila de tipul respectiv. Y — Durata de viaté a unei variabile alocate in HEAP este pand Ia ellberarea spatiului ocupat (cu delete) sau paind la stérsitul executrii programulul = Operatorul deete elibereaz spaliul rezervat pentru variabila a c&rel adresa este rotinuta in P. Dupa eliberare, continutul variabilei P este nedefinit. delete P. 1. Vatiabile de tip pointer catre vatiabile de tip int. Variabila adxt poate ‘feline adrese ale vatiabilelor de tip int. int® adriy adri-new int; // aloc spatiu in MEAP pentru o var. de tip int ‘adei=7; //variabila alocata retine 7 cout struct inreg ‘Cobar mune (201, prenume (20); este Interpretatd ca masiv cu £71181 {81 componente de tip float. in int varatay concluzie, este masiv cu componente de tip pointer si nu pointer catro y i masive. Atentle! Aici se fac multe confuzi main() { inreg* adr; > Intrucat numele unui masiv p dimensional este pointer catre un masiv p-1 adr=new inray cin>>adr~>nun>>adr->pronune>>adr->varetay 4 Cont scade->nuna condi prenunevaratay Gimensional, pentru a aloca dinamic un masiv se va utiliza un pointer catre masive p-2 dimensionale (ultimele p-2 dimensiuni). 1. Alocéim in HEAP un vector cu 4 componente de tip ant. Numele unui Mecanismul alocarii dinamice E2x: ates do vector are tipul Ant (pointer eatre-Ant). Prin urmare, variabila a 7 are tipul int*. Dup8 alocare, ea va contine adresa primului element al in continuare prezentém mecanismul alocarii dinamice a masivelor. Pentru vectorului din HEAP. Din acest moment, pornind de la pointer (retinut in a) ‘inceput, vom prezenta pe scurt legalura intre pointer gi masive, vectorul se adreseazd exact cum suntem obignuiti. =» Un tablou p-dimensional se declara astfel: ats eee Ant laly tip numetn,] tnd... i erence lee ‘Observati modul in care a fost trecut tipui in dreapta operatorului new. Exemple Y Practic, dectararea tipului se face Intocmai ca deciaratia masivului, ins’ + float A(71 [4] [217 ~ am declarat un tablou cu 3 dimensiuni, unde f peinele 2 teat ernie tipul de baza este float. + long b{91{7] [8115]; - am deciarat un tablou cu 4 dimensiuni, unde tipul de baz este Long. Gy, 2 Dectaram in MEAP o matrice (masiv bidimensional) cu 3 tll si S =X coloane, cu elemente de tip double: double (*a) [S]=new double (31517 = Numele tabloulul » dimensional de mai sus este pointer constant catre un ec tablou p-1 dimensional de forma tna}... [mg], care are componentele de : baza de acelas! tip cu cele ale tabloulu. Exemplele de mai jos se refera la = in cazul masivelor, trebuie atentie la eliberarea memoriei (cu deiete) tablourile anterior prezentate: Trebuie {inut cont’ de tipul pointerului, aga cum rezulté din exemplele urmétoare. + A. este pointer constant céire tablouri cu 4) [21 componente de tip float; zs 1. Fie vectorul alocat in HEAP, int *a snew int {41;, Dacd incercém = este pointer constant céitre tablouri cu £71 £81 £51 componente de tip E26: dezciocarea sa prin: deteve. a), i dozalocdm prima componenta, pent Long. c pointerul este de tip int = Un pointer catre un tablou x dimensional cu {1s} {1,]... Cad Corect, dezalocarea se poate face prin: "delete [4] a7" - eliberam ‘componente de un anumit tip se declara astfet spafiul pentru toate componentele (in acest caz avem 4). Observati c& tip (*nume) (2) (a)... Eh) operatorul deiete se poate utiliza si ca mai sus. 20 Capitolul 1, Alocarea dinamic& a memoriel 2. Fie matricea alocata in HEAP; double (+a) (5151 jew double [3] [5]? Eliberarea spatiulul ocupat de ea se face prin "“detete [31 1 Aplicatia 1.1. Programul urmator citeste si afigeazai o matrice. Nou este faptul c& matricea este alocata in RAP. #include main() (dnt myn, 4,4, (fade) £2037 adrenow int [10] {0]7 cout<>my cout<ony for (inOsicmire) for (Je0;3>adr (4) (313 for (in0;Lcmyie+) ( for (Jx0;jensje+) coutscadrlil [i1 cout< vold* Cit_Mat (int m, int n) (int i,4) (*adet) [10]=new int [10] [2017 fox (i#0)i>adet (4) [517 return adri; y void Tip_Mat( int m,int n,int (*adrt) {10)) (int 4131 for (4=0;4emi++) ( for (ud;jensi++) coutcendrt [i] [5]<<" "y cout< void* Suma Mat( int m, int n,int (*adei) (101, int (ade2) (10]) (int 4,4, (adr) (101 =new Ant {10} (2017 for (is0jdemjive) for (J=0;3cns3++) eds [4] [J] =adrd (4) [J]+adr2 (4) (512 veturn adry » Manual de informatic& pentru clasaaXl-a Fl main() {int men, 4,3, (rade) (20), (fadeL) (10) , (adr2) (201 7 cout< cima"? ein>>m; coutccna="7 cindony adri=(int (#) {10} }cit_ Mat (m,a) 5 adr2=(int (*) [10] )cit_Mat (m,n) > agra (int (*) (10) )Suma_Mat (m,n, adri,adr2); nip Mat (mn, ade) : Probleme propuse 1. O variabila de tip pointer cétre tipul integex/int poate memora: a) un numar intreg; 'b) confinutul nei variabile de tipul integex/int; ) adresa unei variabile de tipul integer/int. 2. Fle declaratille urmatoare: Ee Varianta Pascal “Varlanta Cre” type adrint="integer; int tal, *027 adzreal=*ree]7 float “a3; var al,a2:adrint; asiadrreal; Care dintre atribuirle de mai jos este corecta? a) atee7.35; a) aie7.35; b) a3te7.357 b) 0387.35) ) a2i=a3; fe) azeasy @) atssaa a) ateaa; 3. Ce Intelegeti prin HEAP? a) un segment din memorie; 1b) tipul variabileior care retin adrese; ) ovariabilé de sistem in care se pot retine date de orice tip, 4,, Rolul procedurii new / operatoruiui new este: a) deacreao adress; b) dea aloca spatiu pentru o variabilé la 0 adresa dats; ¢) dea aloca spatiu Tn EAP pentru o variabil& de tip pointer; 4) dea aloca spatiu in HEAP pentru o varlabila de un tip oarecare, 22 Capitolul 1. Alocarea dinamic& a memoriei —________apitolul 1. Alocarea dinamica a memoriei 5. Rolul procedutii dispose / operatorulul delete este: 1a) dea sterge continutul unei variabile; b) dea sterge continutul unei variabile alocaté tn HEAP, alocaté in MEAP; 4) dea ellbera spetiul ocupat de o variabila oarecare; 2) dea sterge variabila a care adresa se gasagte memorata in MEAP. 6. Ce se afigeaza in urma executarii programulul urmator? type adrreal="real; include var ai, a2:adrreal; nain() begin C float tat, raz; mew(ai); ai*:937 aisnew float; *aL<3; new (a2); a24:=67 a2imad; writela(a2*:310)) ») 3; ¢) Eroare de sintaxa, 7. Ce se afigeazé in urma executéirl programului urmator, daca se citesc, in aceasta ordine, valorile 7 gi 8? type adzreal=sreal; Hinclude var al, a2,mantadzreal; main() begin Cine #02, #02, ¢man; mew (a1); readin(ai*); atenew int; cin>>*al; new (a2); readin(a2"); A2enew int; cin>>*aa) man:=a2; man=02) egrsal; azeal; ali=man; alsman; weiteln(al*:1:0," ',a24:1:0); couteetance” "< in-cazul listelor, prin acel pointer se poate accesa numai primul element al liste, Apoi, porind de la acesta se poate accesa al doilea element al liste, samd. > — Ulimut element al listei va avea memorat in c&mpul de adresé o valoare cu semnificatia de nici o adresa. Cu ajutorul acestet valori programele vor detecta sfargitul iste. in Pascal, aceasta valoere este nit, iar in C++ ea este 0 Crearea listelor Initial, o variabilé v refine ni. / 0. Presupunem cd, la un moment dat, lista este cea de mai jos, iar v refine adresa primului element (adx,): CO PT] adr; adry adr, v Daca se citeste un nou numar (de exemplu 4), atuncl acesta se adauga intr-o Inregistrare afiat& la Tmceputul liste, In urmatoarele etape: ‘8) Se aloca spatiu pentru noua inregistrare, se completeazé cémpul numerio, iat adresa urmatoare este cea din v, dec! a primului element al liste, Adon ») Vatiabila v va memora adresa noil inregistréri: Programut este prezentat in continuare: 26 Capitotul 2. Liste tiniare “Varianta Pascal, == |) VarlantaCts type Adreaa=*Nods #include Nod=zecora Snfo:ineagers ce adr_urmiAdresay fod* adr urmy fase 5 et aden var viadresay , arrinteger woa* vy procedure Adaug(var v:Adresa; are aritnteger); | void adaug(Nod*e v, int nr) var crnsresas {Noa cxnew Nods begin en>infosney new(e) eovade amavis er sinforenry ver ar_urmi=vi ? void Tip(sod* v) { Wod* c=vy while (c) { coutinfoccendly eze~radr_urmy ) begis - =a ee asin ribet fot indo} Galette Sisco is end; | { Adaug(v.nr): ie i‘ ces cemelas ; toe adaug (v, m2) ¢ weite(‘numars'); readin(nr) ; end) tipi); end. ff. inPescal, nu este permis, ca in C++, s& definim un tip care confine dectarari cee refera la el. Spre exemplu, deciararea de mai jos Nod = recora inforintegers ‘adr_urm = “Nod ends este gresité. Campul adz_uxm face parte din tipul Nod si este definit ca pointer catre acelasi tip (Nod). Conventia de limbaj este s& se declare pe nd cele doua tipur, ca in program. Procedand dupa algoritm, lista va confine informatie in ordinea invers’ tn care au fost introduse. Acest fapt nu prezinté importanta pentru majoritatea aplicatilor. Manual de informatica pentru clasa a Xi-a 27 Un alt algoritm de creare a listel, recursiv, este prezentat mal jos. De aceasti data lista cuprinde intormatile in ordinea in care acestea au fost iniroduse: a6 “Varianta C+ type Adrosa=*Nody include Noderecora infor integer; en adr_urm:Adresa; eet sae Boat names 37 var vingrean; moat v7 tunction adsugsnaresa: Noa adang() wer ciadresay (toa er nevineeger: tne ney begin coutcermumar “7 cim>onr: este ('nra')7 xoadin(ne); fan Af nrc then omen (aoa): begin cvpadeurmngaug() aw(o) copintonny sang =or Setumn cp Bang" intor=nry ) Gauge adr ummsendaug else return 0; > void Tip(wod* v) ond adaug:=nil; lat rig tot oeceade 26 Seca ectecura ; ate ; Meee ( veadaug(); ; et ay a Mal jos este prozentat un subprogram recursiv care tipareste informatie in ordine invers& fata de modul in care se g&sese tn list&: lanta Pascal: [eee Nai procedure Tip_inv(viadresa); void Tip_inv(Nea* v) begin \eie w 4£ veonil then | C tip inv (v-radr_uzm); begin cout<infoccendl7 ‘pip_inv(v*,ede_urm); y writoln(v* info); ? ond; ondy 28 Capitolul 2. Liste finiare © Problema 2.1. Fiind daté o lista liniar’ simplu inlantuité, cu adresa de Inceput v, se cere s& se inverseze legaturie din lst’, adic’ dacd fn lista initala, dupa nodul 4 urmeaza nodul +2, atunei, in noua lst’, dupa nodul 4+, urmeazé nodul 4. © Rezolvare. Functia inv, rezolva problema data. Ea are doi parametri: adresa primului element al lstei (pred) si adresa urmétorului element din listS (cuxent). Practic, la fiecare pes, partea de adres a nodului referit de curent va refine adresa refer de pred (adica adresa nodului precedent), Functia retumeaza adresa primulul nod al liste inversate (adica a ultimului nod in cazul liste! neinversate). inainte de pelul functiei, partea de adress a primului nod listel va trebui s& reliné nil /0. : -VariantaPascal | ~ Varlanta Cr+ function inv(pred, curent: Nod* inv(Hed* pred, ‘adresa) raéresa; Wod* curent) var urniadresa; (Noa urns begin while (curent) while curentcnit do { urmscurent->adr_urmy begin curent->adr_urm=pred; ‘urm:scurent pred=curent} curent=urm) » return predy > Nod* curentev-rade_usmy y->adr_urm=0; Any (¥,curent) + curent :ny*.adz_urmy wh ade_urmienil; Tp); vieinv(y, curent) ; Biptw): 2 Exercitiu. Modificati subprogramul astfel incat acesta s& alba un singur parametru, adresa de inceput a listel. 2.2.3. Operatii asupra unei liste liniare ‘in acest paragrat prezentam principalele operatli care se pot efectua cu 0 Hist liniara simpiu inlanquit, J in prozentarea operatiilor, vom folosi de multe ori desene. Retinefi: pentru orice operatic aveti de efectuat, faceti un mic desen. Va ajuta mult... Orie list’ va fi retinuta prin doua informatii de adres: a primului nod (w) sia Ultimulul nod (s£). Precizém faptul c8, in general, numal prima informatie este indispensabils. Pentru simplitate gi pentru rapiditatea executarii vom refine gi ‘adresa ultimului nod, Structura unui nod al listei este: Manual de informatic& pentru clasa a Xl-a 29 Varlanta Pascal 7 Varianta Cee struct Nod (nt infos Nod* adr_urm; Hu A. Adaugarea unui nod Flind data o lista liniard, se core s& se adauge la sfarsitul ei un nod, cu 0 ‘anumité informatie, in exemplele noastre, un numéir intreg. Se disting dou’ cazuri: a) lista este vida - v retine 0. S8 presupunem o& vrem s& adiéug’im un nod cu informatia 3. Se alocd in HEAP nodul respectiv, adresa sa va fi inv, si cum lista are un singur nod, adresa primului nod este gi adrosa ultimului, deci continutul lui v va coincide cu acela al lui sf. ») lista este nevida Fie lista: Campul de adres al ultimului nod, cel care are adresa in ef, va retine adresa nodului nou creat, dupa care si sf va refine aceeasi valoare. 30 fost necesar s& parcurgem introag adresa ultimului. Capitolul 2, Liste liniare Dacd n-am fi utllizat variablla a€ pentru a refine adresa ultimulul nod, ar fi a list’, pornind de fa v, pentru a obtine procedure Adaugare(var v, Adresa;val:integer) 7 va lade_urmrenily fieve ona else begin Wow (c) 7 af*adr_urmise7 et -inforevaly of adr_urmienil; sfiser ona ond; Nod*a sf, int val) { Moat 7 Lf (vero) { venew (Wod) ; vepinforvaly vo>adr_urm=0) atevs ? else ( cenew (od) 7 af->adr_urmec; e->dnfoaval o=>adr_urm=07 | afser B. Inserarea unui nod, dupa un altul, de informatie data Fie lista din figura anterioara. Dorlm s& adéugéim dupa nodul cu informatia 3, un altul, cu informatia 5. Initial, se identific&’ nodul dupa care se face adaugarea. in cazul de fala acesta este primul. Se alocd spatiu pent tru noul nod. Se completeaza adresa gi anume adresa nodului care urmeaza dupa cel de informatie 3. Apoi, cAmpul de adresa al nodului nou creat: ETE cu informatia 3 va refine adresa nodului ‘Manual de informaticd pentru clasa a Xt~a 31 Un caz aparte apare atunci cand nodul de informatie vai este ultimul in iota. in acest caz we va retine adreca nodului nou creat pentru cd acesta va fi ultima “Varianta C++ void Inserare_dupa(Nod* v, Nod*a af, int val, int val1) { Nod" cay, "47 walle (c->infoleval) viadresayvar sfiadresa; val,valitinteger) + var ¢,diadresa; Guede ae ens begin denew Nod orev @->info=vall? walle o*.info @s adr_urmisc* .ede_urmy oh adr_urmi=dy Af d*.adeurmenil then afied) ondy d->adz_urm=c->ade_uzm; e-padr_urm=4; Af (6->adr_urm==0) sf=d; SES ee ES eee ee eee REE EERE EEE EEE ©, Inserarea unui nod, inaintea altuia, de informatie data Intrucat operatia este asemanatoare cu precedenta, prezentém numai subprogramul care realizeaza operatia respectiv’: procedure inserare_inainte(var viadresa;val,vail:integer) 7 var c,dradresa void Inserare_inainte(wod"e v, int val, int vali) (Coat 6, #47 begin’ Af (y->dnfoxeval) Lf va.Anforval, { d=new Nod ‘then’ d-rinfo=vali; begin d->adz_urm=v? ‘new (a) 7 ved as dnfosevali; d 4 adr_uraiev; else vied Ceevy while (c->adz_urn-> infoleval) Gxc->adr_uray d=new Nod; d-rinfosvalt; d->adz_umn=o->adz_usny revs while ¢4.adr_urm*.infoo val do cime*.ade_urmy e-vade_urmmdy new (a) 7 ) 4*.inforevalty > 4 vadz_urmi=o% .ade_urmy of adz_urmi=dy ona) ona; 32 Capitolul 2. Liste liniare Manual de informatick pentru clasa a XIna 33 D. Stergerea unui ned de informatie data Seesiat T crevt while (c->ady_uam->info Algoritmul este diferit in functie de pozitia tn list’ a nodului care va fi sters - while ct .adx_umm’.infocoval ssvaujoescsneacigcar daca este primul sau nu. do crech adr weny manzo->ade_urmy z : mant=c*.adr_urn; ¢->ady_urmeman->adr_urmy a) Nodul nu este primul. Pentru nodul care va fi sters, informatia de adres a : c*.adx_urmieman* .adr_urm; predecesorului va reline adresa nodulul succesor: 4 if man=sf then af:=c; ends delete man; ——— ieee a Memoria ocupat de nodul care urmeaza a fi sters este eliberatd: Pentru a verifica modul de functionare a subprogramelor de mai sus, este hecesar sa utiizam un altul, care afiseaza lista liniara : - Varianta Pascal Varianta C++ i: procedure listare(v:adresa); | void Listare(Nod* v) ' var o:Adresa; (Nod* o=v; : agin while (e) 1b) Nodul este primut. Fie lista Shite conti do cout cco->infoccandd) begin enc-sade_urmy og ce cise .adz_urmy cout Variabila v va retine adresa celui de-al doilea nod: ; ee Acum putem testa aplicatia, Utilzai seoventa urmatoare: : Varianta Pascal oy _. Varianta C++ var v,se:ndzesay Nod v7, 961 | Tiincogers ine fy | agin pein for tr=1 to 10 do (for (ints Leat0;4s4) aaugare (88) ‘Adaugare(v, 26,1) Lister) uiseare (ey? innerare dpe 38,7,12) Tnsorare.dupa(v,£,7,11)7 Programul este urmatorul: _dupa (v, s£,10,12) 7 Inserare_dupa(v, sf, 10,12) ineorare.cupa (7, a£;2,13)3 Tnserare_dupa(, ef, 1,43) Ea eee Liseare(v)y Eiseare(@s sii Varlanta Pesost se Natlanta Gr ea é inserare_inainte(v, 13,14); Inserare_inainte(v, 13,14); procedure Sterg(var v, void Sterg(Nod*% v, Nod"& sf, a inserare_inainte(v,1,15); Inserare_inainte(v,1,15)7 sfradrecayvai integer)? ne val) Lsearece) ciseare(s7 var c,man:adresa; { Noa* c, *many 1 sterg(v,ef,15)7 Sterg(v, s£,15)7 begin Te (y-binfomevad) | Seoratvat13)1 Stora (v.0f,33)) TE vAstnfoeval then manevs i beeru ey 08,2 Seera(vs 8.42) begin vewevade rm | Tataretwys mocare(w)s Tmentevy vie? ade sem , j ond, , ona 34 Capitolul 2. Liste liniare 2.2.4. Aplicatii ale listelor liniare 2.2.4.1, Sortarea prin insertie Se citesc de la tastaturd n numere naturale, Se cere ca acestea sti fie sortate crescétor prin utlizarea metodel de sortare prin inserfie. Aceasté metoda de sortare a fost studiat’ tn clasa a 1x-a. Ideea de baz a ‘metodei const in a considera primele % valori sortate, urmand s& inseram valoarea k+1 in sirul deja sortat. Prin utiizarea listelor liniare inlantuite, inserjia este mai simpla, intrucdt nu necesité deplasarea componentelor, ca in cazul vectoriior. Pentru simpificarea algoritmului, lista va confine valoarea maxim’ Maxrnt elocaté doja in lista, in acest fel, algoritmul se simplifica pentru ca se pomneste deja de la o lista liniard nevid. Evident, valoarea maxrnt nu va filistata, atunci cand se tiparese numerele sortate. Problema se reduce la insertia unui numéf intt-o listé deja sortats. Mai intl se alocé spatiu in HEAP pentru o valoare, apoi aceasta este cit. Se disting doua cazuri: 1. Valoarea citité este mai mica decat prima valoare a listei. Aceasta inseamn cea este cea mai mica din lista gi va fl introdus prima in lista. Gey Fe sta umatoareg se teste 2 + BOLE] al Noua inregistrare va contine adresa nodului 3, iar v confine adresa noil inregistrari: ~ ERE a 2. Valoatea citité nu este cea mal mica din lista. in mod sigur, nu este cea mai mare, pentru o& am introdus Maxtat in lisié. Dacd nu a fost indeplinte conditia de la cazul 1, inseamna o& valoatea nu este nici cea mal mica. Aceasta inseamnai ca ea va trebul introduss in interiorul ist Manual de informatic& pentru clasa a Xia 35 Va trebui s& identifica prima valoare mai mare decét valoarea citi Intruct, odaté gasité adresa acestei valori, avem nevole de adresa precedent (pentru a putea lega fn list& nou nod) vom “merge cu doi pointer, esi e2, unde e1 refine adresa inregistrarli cu valoare mai mare decdt inregistrarea cits, iar & adresa inregistrérii precedente. <2 Fie lista urmatoare gi se citeste 8, Se identific& prima inregistrare care Ex: ‘ejineo valoare mai mare decat cea ct (in exomplu, 9). > — EAGLE] t 4 Noua valoare se insereaza in lista. 2 © Varianta Pascal type Adresa="Nods Pinclude et const MaxInt=32000; ‘ingo:inveger? agr_urn:aaresas aeract Ned ona: Cine intos Noa adevra) var nytiinteser: i var vadrye,ct idsesay ; int mits per et Nod *v, tear, te, ots veeito( n="); Foadin(e main) new) Ceoutintocey->info) 11 peimad ain ihota begin adr’, ady_urmi=v7 { ade->ade_urmevs vesade; veade? end 2» 36. Capitolul 2. Liste liniare Manual de informatic’ pentru clasa a Xa 37 else(nu @ primal din lista) | else ~ i Algoritmul pe care 1) prezentéim tn continuare furnizeaza o singuré solutio begin // nae primal din lista alunci cand problema admite soluti, In caz contrer, specificé faptul c& problema nu crv Cosvs adiite solute. elt=v* .ady_urm while ¢1*,infocade*.info elev-radr_urmy while (cl->infocadr->info) do { e2e-rade_urmy begin el=el-rade_urm; er=0%.adr_urmy ) eli=ol*.ade_urmy e->ade_urmendy; end; adr-padr_urmecl; of -ad_urms ade; > adr’ .adr_urmi=cly d end; //tiparese ond; env {tiparesc) while (c->infot=Maxint) cmv: { cout<infoccandl; while c*.infocoMaxtnt do e=e->adr_uzmy begin y weiteln (ot info); | cree" .adz_urm ond ond. y Jf, Procedout generat unel valori mai mari sau mai mici decat toate cele & _posibile este deseor' folosit in programare. Realizati cat de mult a simpliicat algoritmut? La fiecare adaugare in lista se face 0 parcurgere a acestela, deci algoritmul are complexitatea maxima 0 (n°) 2.2.4.2, Sortarea topologica Presupunem oa dorim sortarea numerelor 1, 2, .... m, numere care se gasesc int-o ordine oarecare, alta decét cea naturala, Pentru a afla relatia in care se gsesc numerele, introduce un numar finit de perechi (4,3). O astfel de pereche ne exprima faptul c, in relatia de ordine considerata, 4 se afla inaintea lul 3. Exemplul 1. Fie n=3 gi citim perechile (3,1) gi (3,2). Numéiul 3 80 alia Eve: inaintea lui i. §1 3 80 até naintea hi 2. Apar Sova’ solutii posibile: 3,12 313,2/2, Intrucat nu avem nici o informaje asupra relatei dine 4 gi 2. De aici tragem concluzia of 0 astfel de problema poate avea mai multe soluti & Exemplul 2. Fie n=3 si citim (1,2), (2,3), (3,2). In acest caz nu ‘XC: avem solufie. Din primele doua relatii rezult& c& ordinea ar fi 1,2,3, iar relatia a-3-a contrazice aceasta ordine. jn concluzie, problema poate avea sau nu solutie, iar dacé are, poate ti unica sau nu Vor exemplifica functionarea algoritmului pentru (3,4), (4,29, (1,2), 3,2). gi citind perechite Pentru fiecare numar Intre 4 gin trebuie s4 avem urmatoarele informati = numarul predecesorilor; lista succesoriior. Pentru aceasta folosim doi vector conter, vector care refine numarul predecesorilor fiecarui Ie, ke {2.- -n}; = a, care retine adresele de inceput ale listelor de succesor ai fiecarui element. Pentru fiecare element existé o lista simplu intanfuita a succesorilor sal Initial, th dreptul fiecérui element din vectoril contor gi a se trece 0. Citirea unei perechi (4,5) Inseamna efectuarea urmatoarelor operatit © Incrementarea variabilel contox (4) (J are un predecesor, $i anume 3); © adaugarea lui § la lista succesorilor lui s Pentru exemplul dat, se procedeaza in felul urmator: owe ToT To] » =e ETS Valorile inifate ale celor dol vectori, am citit (3,4); 13 - adresa listei 3; ome seo] a oe am citit (4,2); Capitolul 2. Liste liniare am citit (4,4); am citit (1,2); am otit (3,1); jin continuare se procedeaza astfe!: = toate elementele care au 0 in cémpul contr se retin intr-un vector ¢; = penttu flecare element al vectorulul e se procedeaza asttel: + se tipdreste; * se marcheaza cu ~1 cémpul su de contor; * pentru toti suecesoriis&i (aflaf tn lista succesoriior) se scade 4 din cémpul contor (este normal, intrucdt acestia au un predecesor mai putin); = se rela algoritmul daca nu este indeplinita una din condijile urmatoare: a) au fost tipétrite toate elementele, caz in care algoritmul se inchele cu succes; ) nu avem nici un element cu 0 in cémpul contox, caz in care relatile au fost incoerente, 39 Tiparese 3, scad 4 din predecesorii lui 4 gi 2, ‘marchez cu =1 contorul luis. Tipdresc 4, scad a din predecesotii lui 2 gi 4, marchez cu ~1 contorul lua, Tiparesc 1, scad 1 din predecesori lui 2, marchez cu ~3 contorul lula. Algoritmul are multe aplicati, ca de exemplu: - ordonarea unor activitati,atunci cand ele sunt conditionate una de alta; + ordonarea unor termeni care se cer explicati, pentru a-i putea explica prin alti deja prezentati Aigoritinul are complexitatea O(n*). Odata sunt n extrageri gi la flecare extragere se parcurge lista succesorilor unui nod. 40 Capitolul 2. Liste liniare Varlanta Pascal Varianta C++ type rof=*inr; inrerecora sucorinteger: urmiret, ond; vootorsarray [1-.100] of integers vactadsarray [1..100} of vee; var n,m, i,j,krinteger; contor, crvector; arvectad; gasit boolean; procedure adaug(i,j:integer) ; var o, atref; begin eontor{3] sreontor 3] +2) ermalily new (4) 5 as .urmesnily ar ouccs=37 if cenit then a[i}:=a else begin while ¢*.umeonil do procedure actual ( var c:ref; Anteger) ; erealily while c end; meny repeat keels gasit:sfalee; for ii=L to n do Af contor{il=0 ‘then begin gasitretrue; arent, otkl rei; raked; contor {41 :=-2 endy | for isi to ket do ‘begin actual (cli) 7 weiteln (cll); end; yatil (not gasit) or (m=0); Lf m0 then writeln('totul @ okt) else writeln(‘rolatit ‘contradictors ona, 2.2.4.3. Operatii cu polinoame ‘n acest paragrat vom prezenta modu! in care se pot programa operatii precum ‘adunarea, scéderea, inmultirea si Impéirrea polinoamelor cu coeficienti reall 88 observam ca, in acest caz, utilizarea listelor liniare simplu inlantuite este necesara gi, exemplul in sine, constituie un argument pentru utiizarea acestora, 2. veces? 8 presupunom c& un polinom va fi memorat cu ajutorul unui vector. Fiecare coeficient va fi memorat de o component a vectorului, De exemplu, polinomul: Loxx+6.00°4390c+2, poate fi memorat cu ajutorul vectorului (20,6,3,2). Dar dac& aver polinomul 3xx%*+1, cum procedam? Este necesar s& avem un vector cu 1457 de componente, dintre care numai prima si ultima sunt diferite de 0, Este ficient s& folosim vectori? Evident, nu. 2 Atunci2 42 Capitolul 2. Liste linare Pentru memorarea unui polinom (prin coeticienti ul) vom utliza o list tniara simpli inlanuié. Fiecare nod al lisei va tine, in aceasta ordine, Goefcientul si gradul unui _monom. Pent simpiicarea operator cu Polinoame, un polinom va fi retinut in ordinea descrescatoare a gradelor. De exemplu, pentru polinomul axx"+ 21°42, vom avea: F ‘Mai jos, prezentam structura unui nod al iste: SE Varianta Pascal “ Varlanta Cre type a as struct Nod sdtRogetody { float coef record int grad; 9a Hod* adr_urmy grad:integer: ites adr_urm:adrtod; ena; 1, Pentru @ adduga un nod liste liniare i r simplu intan{uite, atunct cand aceasta se sreeazé, vom tiiza subprogramul urmator, adaug. Parameti de intrar® sunt sxcesele de Incoput gi de strait ale Het. Desigu, ee putea eva parametul prin iresa de sfarsit a listei, dar, prin transmiterea acestui barametru, adaugarea unui nod ta sfarsitul ste! se poate face cu mult mal roped, peniru cd nu mai este necesara parcurgerea intregil liste. : Varianta'Pascal procedure adaug(var v, e€iadriod; griinteger;cf real); var cradztiods begin new(s) 7 eh gradregr; ch .cosf inet; eh ade urmieni2) Lf vanit then begin viser Bfimcy ena Varianta C++ void adaugiNoars v, Nod*& sf,int gr, float cf) (Nod® ¢7 | ceney Nod) co->grad=or? e->eoef=cf; { sf->adr_umm=c; ste; begin f*.adr_ummise; ef:sc; ena end; Manual de informatic& pentru clasa aXi-a SESE a ‘2. Pentru a crea lista asociat’ unui polinom, vom utliza functia urmatoare, care dupa oe creeazé lista, rotumeaza adresa ei de inceput. Pentru a putea introduce Watele, se cere, de ia inceput, numdrul de "termen (monoame) ai polinomului Este foarte important ca monoamele 88 fie introduse fn ordinea deserescatoare a gradelor, pentru ca functia nu realizeazé ordonarea acestora. Pentru a crea lista se tilizeazd subprogramul prezentat anterior, adaug. Exercifiu. Modificatl funotia astfel incét datele de intrare 88 se g&seascd fntr-un fisier text. De asemenea, se ‘core ca functia s8 sorteze monoamele in ordinea descrescatoare a gradulul. Varlanta Pascal Warlanta a function crePolinom(nr_termeni: | Nod" crePolinom(int nr_terment) Integer) radzttod; | ( var gradul, i:integes cout<<"Date polinom "< ve.grad) 7 views. ade_urm » dreiely end; writein writeln; end; cout<gradsze2->grad) Af c1*.grad=o2*.grad (Af (ci->coet+c2->coef) ‘then adaug(v,8£,cl->grad, begin ‘el->coet+c2->coes) 7 Af c14.coof+ea*.coofe>0 elsci->ade_urmy ‘then e2nc2->adz_urmy adaug(v, sf, 01*.grad, » o1*,coef+62*.coef); | else eliecd*.adz_urm; Lf (cl->grad>e2->grad) e210 .adz_urmy { adeug(v, 9£,c1->gead, nd ‘el=>co0e) else elscl->adr_urm; Af c14.gradre2*.grad + then else begin ( adsug(v, s£,02->graa, adaug(v,s£,c14 grad, e2->coof) 7 cl .cooe cd=02->adr_urmy elizet*.ade_ueny y end af (oD) else while (1) begin { adaug(v, s£,c1->geaa, adaug (v, 8f,02.grad, c1->coes) ; ©2*.coes) 7 el=cl->adr_urm; 102° .ade_urm} > else | Af cleonil while (c2) | ‘then ( adaug(v,8f,c2->graa, | while e1<>nil do €2->c008) begin e2ne2->adr_urny adaug(v, sf, 614.grad, > el* coat) 7 return vi eLtse1* adr_urm; > end else while c2grad, viienily =(7->0008)) 7 while ve> nil do vev->ade_urny begin > adaug (v1, s£1,v4 grad, return vis avi oot); y view’ adr_urmy end; nogativisva; end; 7. inmuttirea unui polinom cu un monon. Pentru a realiza aceasta operatic uilizam functia mulMonom. Functia primeste ca parametri de intrare adresa de inceput a listel care retine un polinom, gradul monomului si coeficientul séu. Functia construieste un nou polinom, cel rezuitat in urma inmultiil polinomului dat cu monomul si returneaza adresa do inoeput a listei care il refine. | Varianta Pascal function mulfonon(v:adxod; Nod" multonon(Hed* v, int or, grrinteger/cf:real) :adzNod float c£) var vi, sf 1adzWod; {Nod vE=0, toy begin while (v) vérenity ( adaug (v#, s£,v->gradtar, vile v<> nil do | ‘y-booot tof): begin veve>ade_ army adaug (vf, sf,v*.gradear, » Ye eoee*ce) 7 return VE views adr_urm: , end multtonom:=v£; ond 8. inmuttirea a dou’ polinoame. Operatia este realizaté de functia mal. Ea are ca parametri de intrare adresele de inceput ale listelor care retin polinomul deinmulit §1 polinomul Inmuititor si returneazé o noua listé In care se gaseste potinomul rezuttat Produsul se objine inmultind, cu fiecare monom al polinomului inmulitor, polinomul deinmuitt si adunarea tiecarui polinom astfel obinut la rezulta. Odservati cum se gterg polinoamele intermediare, care nu mai sunt necesare! 48 49 Capitolut 2. Liste liniare Manual de informatic& pentru clasa a Xi-a Varianta Pascal Varlanta Gre nanuy enctor steerer, oat polemul (imp, factor); Function mui(vi,v2sadetiod) adzxed; | Nog* mul od vi, Nod* v2) i potsemil timp, factor) 7 weerutfactor) yous var v,vman,vaani:adriody (Noa v=0; ; Beorg (factor)? Nod nearne begin white. (2) ' ege=nogativ (pol) + seeTU (DOLD ea) vrenity (Hod tyman=0, ‘ymant sters (pol): Seecgtneey eee while v2enil do ‘ymansmulifonon(vi, rest rmadun (rest, neg) 7 stare (nea): begin va->grad, v2->coeE) stargines) ; 7 ‘vman remultfonon (vl, v24.grad, wnaniev) : ena; > ‘v2 .coet)7 veadun (¥,vman) 7 i end: sterg(vman) ; i (ee vieadun (v, van) 7 sterg(ymant i ; Seat aneteeay iq Pentru a testa subprogramele prezentate, puteti folosi programul urmator, sterg(vmani); i) i : care citeste doud polinoame gi calculeaza suma, diferenta si produsul lor. De a vetumn v; i asemenea, se calculeaza si cétul si restul imparfiri celor doua polinoame. > : i “Varienta Pascal | Varianta C++ struct Nod : (float coets 3. Impartirea polinoamelor. Operatia este realizat de subprogramul divp. Noderecora ee eae Acesta primeste ca parametr! de intrare adresele de inceput ale listelor care retin : coef treal; A ct Ppolinomul deimpartit $i polinomul impaitor. Susprogramul retumeaza adresele de grad:integers Doda daatatpeeuancees inceput ale listelor care retin polinomul cat si polinomul rest, iniial, restul va fl adr_urmsadsNods ae deimpar{itul (se consiruleste lista care retine deimpartitul). Apoi, cat timp gradu! i a eee (int mn; . restulul este mai mare sau egal cu gradul impartitorulul, se aflé monomul cu care see east ost radznoa | cout<<"ltr torment primal Se Inmuifeste cétul pentru a seddea din rest, se calculeaza produsul dine eer polincarts cimom monomul astfe! determinat si cét si se scade polinomul astfel rezultat din rest, { subrogranele prozentate } oat pincropolinen(@); obfingndu-se un nou rest. $i aici, listele continand polinoame care nu mai sunt : ee athe cece prima Set and tueeseschnseas Heer eee i polinom='); readinim); | yoat pawcrePolinom(n)? pliscrePelinom (nm); 1) guna : : : Weite('Nr terneni al doilea Nod* =adun (pt, D2); i : polinom="}; readin(n); | Couecersuna entetgrad,dein->coof); agis(d): iiisw)? pene doinsdein-radr_urn : { produs ) Grice ‘adaug (rest, sfrest, Hy : pis) (D1,p2) + Hoa* cat, *r* Salat oraacasiastenety while (rest->grad>=imp->grad) writeln(‘produsul este‘); aiyptntsgarcat/ iene asereaeine ae { costs rest~>coet/ atis(D) recteatal este" <cinp*.grad do gradulerest-ograd~ atyp tpt eps cat rest) courcerrest ester adaug (cat, ofeat, gradul, coat); mamngdescese, ebaeese? fi else afis(rest); ei # ‘sradul,coot)1 ond. at Capitolul 2. Liste liniare 2.3. Liste liniare alocate dublu fnl&ntuit BAY Deefinitia 2.3. 0 lista alocaté dublu inlaintuit este o structural de date de WARS forma: [Lo [ins [oars [Taos Tits [adr [7 ove Toa] ad dn adr h Avantajul utiizarii listel alocate dublu iniantuit este dat de faptul c& o astfel de lista poate fi parcursé In ambele sensu Operatile pe care le facem cu o lista dublu Infan{uitd sunt urmatoarele: 1) creare; 2) adugare la dreapta; 8) adaugare la stanga; 4) adiugare in interiorul liste; 8) stergere din interiorul liste; 6) stergere la sténga listel; 7) stergere la dreapta listel, 8) listare de la stanga la dreapta; 9) listare de la dreapta la stanga. 2.3.1. Crearea unei liste liniare alocate dublu inlantuit O lista dublu inlanfuité se creeaza cu o singura inregistrare. Pentru a ajunge la numarul de inregistréri dort, utilizim functii de addugare la sténga sau la dreepta. In programul de fafa acest lucru este realizat de functia creaxe. Aceasta funclie realizeaza operatille urmatoare: + cttirea informatie’ numerice; + alocarea de spatiu pentru tnregistrare; © complotarea inregistrarii cu informayia numeric’; ‘+ completarea adreselor de legaturd la sténga gi la dreapta cu 0; Variabilele tip referints b si s vor c&pata valoarea adresei acestel prime inregistrati (b semnific& adresa inregistrarii cea mai din sténga, = adresa ultime! inregistréri din dreapta), : 51 Manual de informatica pentru clasa a Xl-a Cream lista cu un singur element: . Cel eta ¥ 2.3.2, Addugarea unei inregistrari la dreapta Aceasté operate este realizata de funciia adax. Pentru adaugarea unel {nregistrat se realizeazé urmatorii pasi: + citirea informatie! numerice; ‘© alocarea spatiului pentru inregistrare; + completarea adresel a dreapta cu 0; * completarea adresei din sténga cu adresa celei mai din dreapta inregistrari (refinute in variabila 8); ‘+ modificarea campului de adresé la dreapta a inregistrarii din cu adresa noli inregistrér; © ava lua valoarea noil inregistrari, deoarece aceasta va fi cea mal din dreapta. Zeb, Mtuaie ia droop inrogistarea 3. Ss: 2.3.3. Addugarea unei inregistrari la stnga A rcoasta operaie va este propusa oa exerci 2.3.4. Addugarea unei inregistrari in interiorul listei Aceastd operatie este realizata de funcfia Inelud: and Integistrarea cu informatia © parourge lista de la stnga la dreepta cdutan 2 fc Fumeraé m,n dreapta cdreia uimieaza s@ introcucem noua inregistrare; « citeste informatia numeric’; + aloca spatiu pentru noua Inregistrare; Capitolul 2. Liste liniare © completeaza informatia utla; © adresa sténga a noil inregistrari ia valoarea adresei tnregistratll de informatie Utila; * adresa stang& a inregistrarii care urma la acest moment inregistrarii cu informayia numerics m capats valoarea adresei noil nregistrari; * adresa dreapié a noliinregistrari ia valoarea adresei dreapta a inregistrérii cu informatia utild m; + adresa dreapta a ‘inregistrari cu informatia numericdé m ia veloarea noli inregistrar Sx: In lista urmatoare adugam, dupa inregistrarea 3, ‘inregistrarea 5: Propunem ca exercifiu reatizarea unei functfi de adaugare in interiorullistei a unei inregistrai la sténga Inregistréii cu informetia numericd. m. 2.3.5. $tergerea unei inregistrari din interiorul listei Aceasté operatic este realizata de functia stexg. Operatile efectuate de aceasta functie sunt urmatoarele: * Se parcurge lista de la sténga la dreapta pentru a ne pozitiona pe inregistrarea care urmeazéi a fi stears&, + cémpul de adres dreapta al inregistraril care o precede pe aceasta va lua valoarea cémpului de adresa dreapta al inregistrii care va fi sterse; reac Manual de informatic& pentru clasa a Xl 53 © cémpul de adres stanga al Inregistrarit care urmeaza thregistrarii care va fi sterse va lua valoarea cémpului de adres stanga al inregistratli pe care 0 stergem; «90 olibereaza spatiul de memorie rezervat inragistraril care se sterge. jin lista de mai jos se sterge elementul cu informatia numeric& 5: od 2.3.6. Stergerea unei inregistrari la stanga/dreapta listei A wooste souk operatii sunt propuse ca exerci 2.3.7. Listarea de la stanga la dreapta listei Aceast operatie este realizaté de functia tistare care realizeaza urmaitoarele operati: + pomeste din sténga liste; + aldi timp cat nu s-a ajuns la cepatul din dreapta al liste, se tiodreste informatia numerica si se trece la inregistrarea urmatoare. 2.3.8. Listarea de la dreapta la stanga listei FZ oporatia se propune ca exereiiul Capitolul 2. Liste tiniare {In continuare sunt prezentate subprogramele i un exemplu de utilizare a lor: Varianta Pascal type ref=sinr; dnr=recora aires; nrtinteger? ad:zef ends var b,a,crref nymAtinteger; procedure creare(var b,a:ref)) begin weite(*ns"); readin(n): new(b); b*.ner=nz Dsvastenil; b*,adsenily ied ena; procedure addz(var sixef); var diref; begin write('n= new(a) ; @*.nrisay a*.as: @*sadzenity stiadied; eid ond} 2 readin(n); procedure listare(b:ref); var ds while deonil do begin writein(a*.nr)7 disa* sad end end; procedure includ (medntegersb:ref) ; var d,orxef; #include struct Nod (Nod *as, } ant ar? ” Nod *b, #8, 6; int nym, iy aa; void Creare (Nod*é b, Nod*s 5) { cout<<*n="; cin>on} benew Nod) benreny beageb->ad=0; eeb; > void Addr (Noa*s 2) ( coutec*ne") cin>ony Nod* denew Nod; @-pnreny ) void Listare(Nod*@ b) ( Noa® dab; white (a) { cout<nre void Includ(int m, Nod* b) (Nod *d=b, te; while (d->nrlen) ded->ads cout<ony ‘e=new Nod; ->aw=dy Manual de informatic& pentru clasa a Xi-a 55 procedure sterg (m:intege: beret) var diref) begin ib; while a*.nrom do d:= a+ sagt ads=d* ad @s,ad*sagi=d*.a5; aispose (a) ond; + ads begin ‘weiteln(‘Craare lista cu o writela(‘acun listez de la stanga 1a dreapta’); Listare(b); weiteln('Zncludem 1a areapta o inregistrare'): weite(‘Dupa care inzegistrare se face includerea? '); readin(m)? includ (mb) 7 weitoln(‘acun Listes de la atanga la araapta'); Listare(b): weitela(‘Acum stergen o inregistrare din interior‘); weite('ce inreg. stergem? *); veadia(n) storg (mb) 7 weiteln(‘Acun Liste: do 1a stanga 1a Areapta'); Listare(b) main() { cout<<"Creare lista cu o singura inregistr. "<>m) for (islicemit+) Adar(e)s coutcc"Acum liste: do la stanga la dreapta"<>m Enelud (m,b) 7 cout<<"Acum Listez de la stanga 1a dreapta*< + adugarea unul element in stv ae cnevens-ealal iar ioe pronierirartapioniaes : + eliminarea, consultarea sau modificarea ultimului element introdus tn desde agree; (Node eb; i stv, ervadind* sad waile (G-onr len) a-d->a i a adice Secattea treat ‘ Stiva functioneaz& pe principiul L2FO (Last In First Out) - “ultimul end} i intrat primul iesi¢. > { Analizati programul urmator, care creeaz’ o stiva prin utllizarea unei liste liniare simplu inian{uite. Adéugarea unui element in stiva se face cu sudprogramul Puss, iar eliminarea, cu subprogramul Pop. Varful stivel este refinut de variabila v. Capitolul 2. Liste liniare Ei : _ Varianta Cr+ type Adresa=*Hods | Winctude Nod=recora struct Nod inforinteger; ine intoy adz_inap:Adrena; | © Node adz_inap, ena; los var vinaresa; | Noae wy niintegers | sine ay procedure Push(var viadresa; | vold Push (iiod*e v, int n) atintege:)7 {Nod* cy var c+Adzesas if GW) begin { ve new Hod) 12 vent vovinfo=ns ‘then begin vobadz_ing new(w) > veinfoseny o1s0 velar inap:enil; (c= new Nod: ena c->info=ns else begin e-padr_inapevy new(e) 7e*-infoz=n; veer eh vadr. Snap: > vitor > eee yold Pop (oats v) % (Noa er procedure Pop (var v:Adresa); if (lv) var c:Adresa; coutcctstiva este vidaty begin else if venti then Conv: writeln(‘stiva este vida') cout<<"an scos" else begin << e->infoccendls erev vev->adr_inap; weitoln(‘am scos', ¢*-into); delete c7 view’ ade_inapy > dispose (e) > ena main) ena; € Push(v,3); Puoh(v,2)7 begin Push(v,3)7 Push(v,2)) Push (w,2); Pop(v)} Pop(v) + Pop(v); Poptv) Pop(y) Pop(v); PoD(W) i od. y 2.5. Coada implementata ca lista liniara simplu nlanquita capa. Definifia 2.5. O coada este o listé pentru care toate inserdiile sunt facute la unul din capete, iar toate stergerile (consultarle, modificarile) la celalalt Coada functioneaza pe principiul FIFO (First In Fixet Out) - ‘primul intrat primut iesit. Manual de informatica’ pentru clasa a Xl-a 57 Alocarea dinamic& inkinfuita a cozii. © variabilé v va retine adresa elementulul care urmeaza a fi scos (servit). O alta, numita ef, va retine adresa utimului element introdus th coada. Figura urmatoare prezinta 0 coada in care primul element care urmeaza a ti scos are adresa in w, iar ultimul introdus are adresa in sf. _ ef adz_urmsAdrei end; var v,of:adresay niinteger; procedure Pune(var v, ‘sf :Adresa;n: integer) ; var c:Adresa; begin if venil then begin new(e) 1 va sinfor=n; vs ladr_umn! efinvs ond else begin new(e) aff .adr_urm:sc? c*.infor=ny c*sadr_urm:enil; stize end ends wail; procedure Scoate(var v, ef :adresa) 7 var cradresay begin Af venil then writein('coada este vida") aispose(c) ond; Varianta Pascal Varianta C++ type Adresa="Kods #include Nod=recora struct Nod inforintegers {int infos Wod* adx_uxm; void Pune(Hod*e v,Nlod’@ sf, int n) { Rod* cy ‘of->ady_urn=cy o->infons e->adr_urm=0; sfsc7 3 void scoate(nod*e v) { Woa* 7 if (iv) cout<<"coada este vida"<infoccendl; yev-padx_uxny delete ¢7 2 58 Capitolul 2. Liste tiniare { subprogran de stare a @lenentelor aflate in coada ) 11 aibprogian de itetare @ hegin ain () Pne(v, 08/3); runetv,st,2), | susace,ef,4)7 manotv,e Pune (#s88,3)) ulate Puno(e,at/3)) tistasetes Scontatvred)) ‘ulscarcen)? Scoste(e); Ziotare tn Scoate(wiaf)) tistace(yys Secate(v)) idsteretv)s Bcoate(viat); tistaretn); | Secaeeiey, pagearst’)? ona. , Probleme propuse 1. Asociati fiecgrui tip de listé denumit in coloana di t in sténga_desenul Corespunzator din coloana alata in partea dreapié a tabelului urmator, serind cifra asociata fiecarei litere: eo Ep a A. list liniara simpiu tniantuita 1 [> ist4 neliniard simplu intantuts — | 2, Manual de informatica pentru clasa a Xi-a 59 4. Stiind c& adresa de inceput a istel reprezentate in desenul urmator este memoraté in variabila p i cd fiecare nod al listei refine in cdmpul inf numarul serls in desen gi In cdmpul adr_urm adresa elementului urmator, stabilti ce reprezinta expresia de mai jos. = Narlanta Pascal pf -adr_urm*.adr_urm* ne THE} 1a) este 0 expresie incorect’; b) valoarea memoraté in nodul al treilea (valoarea 2); ) adresa elementului al treilea (elementului ce memoreaza valoarea 2); 4) valoarea memorata in nodul al doilea (valoarea 4); ) adresa elementului al doilea (elementului ce memoreaza valoarea 4). p-padr_urm->ady_urm->nr 6. Stiind c& adresa de incoput a listei reprezentate in desenul urmator este ‘memoraté in variabila p $i o flecare nod al listei refine in cmpul in€é numérul scris in desen si in cémpul adx_urm adresa elementului urmator, stabil! ce teprezint& expresia: p*-adr_urm*.nr*.adr_urm p->adr_urn->nr->ade_urm I] oeotson 2. Care dintre noduri liste! urmatoare (identficate prin numere inite 4 si 4) este primul element al listei? 2) nuenista un prim element C. lista liniaré dublu tnlantuita 3a D. lista neliniard dubtu tninquita — | a, TI aya b) 4 ©) 2) 8. Dace 0 lista format din dou noduri (identifcate pri cate prin numerele 4 si 2) are Proprietalea c& slementul urmator noduiul 2 este nodul a si nu existé un element urmator nodului 2, atunci spunem ca lista: 8) este circulara; ») este liniara simplu inlantui ) nueste liniaras; 4) este liniara dublu inisnquits, 2 }—[3 a) este 0 exprosie incorect’ ‘») valoarea memorata in nodul al dollea (valoarea 4); €) adresa elementului al trellea (elementului ce memoreaza valoarea 2); 4) valoarea memorata in nodul al trellea (valoarea 2). 6, Stiind c& exist’ o listé liniard simplu inl&nfulta nevida, fiecare nod retinand tn ‘campul ref adresa slementulul urmator al istel, gi gtiind c& variabilele v gi @ retin adresa primului si respectiv adresa ullimului element al listel, explicafi care este cefectul instructiunil: | Narlanta Pascal” 8’ .refev j~>refsy 7. $tiind ca exista o lista liniard simplu tnléintuités cu cel putin dou’ noduri, flecare od refinand in campul uxm adresa elementului urmator al listei, si stiind c& varlebilele ind si £in retin adresa primulul gi respectiv adresa ultimului element al Iistei, explicati care este efectul instructiunii: 60 Capitolul 2. iste liniare Narianta C++ nis ,urmefin ini->urm=fin 8. Scriefi un subprogram care creeazé o lista liniaré simplu inlantuita in care, fiecare nod, pe langa informatia de adresa, va contine o variabllé de tip struct care reline date referitoare Ia un elev. Functia va returna adresa primulul nod al listei, Datole se citese de la tastaturd. * numele: 20 de caractere; + prenumete: 20 de caractero: * un vector de numere reale cu. 3. componente care refinnotele elevului 9, Sorieti un subprogram care afigeaz’ pe monitor numele, prenumele gi media generala a fiecarui elev din lista de mai sus. Functia va primi ca parametru de intrare vartul liste 10. Scrietio funcfie care retumeazé media generalé a elevilor care se gasesc in list 11, Scrieti un program care creeaza si aliseazé o list& liniara simplu inlantuita Fiecare nod al listel contine, pe lénga informatia de adres, un numa natural mai mic sau egal cu 4.00000. Numerele se gases, toate pe o linio, in ordine, separate prinr-un spatiu (blank) in figiorul text "Lista. in’ 12. Scrieti un program care creeaza sl afigeaza dou’ liste liniare simplu inléntuite. Prima list va contine, in ordinea citiri, numere pare, iar a doua va contine, in aceeagi ordine, numere impare, Numerelo se citesc din fisierul text "numere .in’. Ele se gasesc toate pe o linie si sunt separate prin cel putin un spatiu. De exemplu, daca fisierul text contine numerele: 0 25 9 8 3 67 1, atuncilistele vor 18. Scrieji un subprogram care creeaz’ figierul tox! "Liste. out” cu informatilo atlate in cele doua liste de la problema anterioard. Prima linie va contine numerele din prima list, a doua numerele din a doua lists. Exemplu: pentru listele din figura de mai sus, fisierul va fi liniat 0 286 Linia2 59374 14. Scrietj un subprogram care adaugé un nod /a sférsitul unei liste liniare simplu Inlantuite. Flecare nod al listei confine, pe lang’ informatia de acres, un numéir real. Subprogramul are ca parametri formali adresa primului element al listei si valoarea reald care se adauga. Manual de informatic# pentru clasa a Xl-a 61 18. Scriefi 0 functje care adaug’ un nod fa Inceputul unei liste liniare simplu Inlintuite. Fiecare nod al listel contine, pe lang informatia de adres’, un numar teal. Funcfia are ca parametti formali adresa primului element al listel si valoarea 1eala care Se adauga. Ea retumeaza noua adres de inceput a listel. 16. Se d& o list liniaré simplu Tnignfuit& alo carol noduri retin, pe lénga informatie de adresd, numere naturale cu o singurd cifra. Lista are cel putin un nod si cel mult 5 nodur. Se cere 8 se sctle o funclie care calculeaz’ si afgeazé valoarea Intreaga obtinuta prin tipirea cifrelor memorate in listé In ordinea citi, Functia va primi ca parametru de intrare vartul listei. Exemplu: pentru lista de mai jos se afigseaza valoarea 956: PREREPLI 17. Prin operatia de concatenare a doua liste liniare simply Inl&nfuite se obfine oa {rela lista liniar& simply inlantulta care contine, in ordine, nodurile primei liste, urmate de nodurile celei de-a doua liste. $8 se scrie 0 functie care concateneaza dou liste date prin adresele nodurllor de tnceput. Functia va returna adresa primului nod al noii liste. 18. Se citeste un figier text ci fre.. in care confine, pe o unica linie, numai numere naturale intte 0 gi 8. Numerele nu sunt separate prin spatil. Se cere sa se formeze © lst liniard simplu inlanfuita Th care flecare nod retine o cif’. Exemplu: Pentru 01396 se obtine lista: 19. Sa se scrie 0 functie care primeste ca parametru de intrare adresa unei liste liniare simply inléntuite gi are rolul de a inversa nodurile aflate pe prima si ultima pozitie. Functia va retura adresa primului nod al listei 20. Scrieti un subprogram care elibereazé spatiul ocupat de 0 lista finiard simplu Tntesnquit. 21. Sctiefi un subprogram care memoreaza un tablou bidimensional cu m fini sim coloane ca m liste liniare simplu inlantuite, unde fiecare listé memoreaza, In ordine, elementele une lini Exemplu: pentru tabloul urmator se obtin stele: (0253) 22. Se GA o listd liniara simplu inlantuité in care fiecare nod refine un caracter. S& se sctie 0 {unctie care depisteaz daca lista contine caractere distincte sau nu. Ce valoate trebuie sa intoarcd o astfel de functie? RRS ? 62 Pee ____Capitolul 2. Liste liniare 23, Se da o lista tiara simplu inkantuit& in care fiecare nod retine o liter’. Se cere 88 se sorie 0 functie care depisteazé dac& cuvéntul format prin elaturarea lterelor citite este sau nu palindrom (se obtine acelasi rezultat dacé cuvantul se clteste direct sau invers). De exemplu, lista urmatoare confine un cuvant palindrom: 24, in cazul tn care pentru o lista liniaré simplu inlantuité cémpul de adresa al ultimului nod refine adresa primului nod, se obtine o lista circulara: - >| Creat! o lista circularé fn care fiecare nod retine un numéir natural. De asemenea, serieti subprograme de inserare si stergere a unui nod al liste’ create. 26, Se citeste 0 permutare a numereior 4, 2, .., . Se cere ca, prin utlizarea unel liste circulate, 88 se atigeze toate permutarile circulare ale acesteia, Exemplu: Se citeste 1 2 3, Sevaatiga'd 2 3,234,342. 26. Scrieti un subprogram care transforma o list liniar’ simplu inkintuité tm una, dublu inkintuita, 27. Dupa cum stiff, nu se poate iuora in mod direct cu numere naturale oricat de mari, Din acest motiv, vom memora un numer natural ca o list liniaré simplu fnlanjuita. De exemplu, numérul 5610 se va memora sub forma de mal jos. Scrieti tun subprogram care citeste de la tastaturé cifrele unui numér natural, noapand cu cifra cea mai semnificativa, si memoreaz& ca lista liniara simplu inlantuitd, 28. Scrieti un subprogram recursiv care primeste ca parametru de intrare adresa Une’ liste liniare simplu inlantuite care refine un numar ca mal sus $l aflgeaza numarul. De exemplu, pentru lista de mai sus se afigeaza 8610. 29, Scrieti o functie care, aduna dous numere naturale memorate ca mai sus gi retumeazé adresa de inceput a numarului sum, memorat ca lista. Exemplu: din primele liste rezultd a treia list&: Manual de informatic’ pentru clasa a Xia 63 80. Scriot o functie care calculeaz’ produsul dintre un numér natural memorat sub forma de listé gi un altul, cu o singuré cif, transmis ca parametru.” Functia rolumeaza adresa primului nod al listel care contine rezultatul. Exemplu: numarul de mai jos so inmultoste ou 3 gi rezulta: 31, Scriti o functio care inmulteste coud numere naturale memorate sub forma de {ste si retumeaz’ adresa de tnceput a listei rezultat. 32. Lucrare in echipa. Scrieti un ansamblu de subprograme (numim ansambiul WUMERE_MART) care s& ne ajute 54 lucrém cu numere intregl, orieat de mari, iemorate sub forma de liste. Utlizatorul poate efectua adunarea, scdderea, inmuljrea si impartirea @ dou’ astfel de numere. De asemenea, vor exista functi care $4 permits efectuarea comparatilor inte doud numere: mai mare, mai mic, egal, mai mare sau egal, mai mic sau egal. 33. Prin utilizarea asamblului numit NoMERE_MART, calculafi maximul an humere Intregi, cltite de la tastatura. 34, Prin utlizarea asamblului numit sme MARZ, sortati crec&tor n numere Tntregi, tite de ta tastatura. 35. Prin utiizarea asamblulul numit NuMERZ MARZ, calculati nt, unde n este citit de la tastatura. 36. Prin utilzarea asambiului numit wumeRe_ARz, calculati: >)” kt 87. Lucrare in colectiv. Se numeste matrice rar o matrice in care majoritatea ‘elementelor sunt nule, © matrice raré va fi memorata cu ajutorul a dou’ liste liniare simplu inl&ntuite, una continand veloriie nenule, alta numarul de ordine al lor, numar rezultat prin parcurgerea pe lini a matricel. Scrieti un set de subprograme cu alutorul c&rora sa se poata efectua cu ugurinta operatil cu matrice rare: adunare, scddere, Inmuljre, Exemplu: matricea urméitoare se memoreaza aga cum se vede: woes A=|0 500 oo03) Depp} He] Raspunsuri la testele grila 1. Se realizeaza asocierile: a-3, 8-1, ¢-2, D-¢; 2a); 3.b) ;4.b);5.a) 4 Capitolul 3 Metoda DIVIDE ET IMPERA 3.1. Prezentare generala Divide EF IMPERA este 0 tehnicd special gi se bazeazd pe un principiu extrem de simplu: descompunem problema in doud sau mai multe subprobleme (mai ugoare), care se rezolva, iar solufia pentru problema initial se obtine combindnd solutile problemelor in care a fost descompusa. Se presupune o& fiecare dintre problemele in care a fost descompusé problema initialé, se poate descompune in alte subprobleme, la fel cum a fost descompusd problema inttiala, Procedeul se reia pana cand (in urma descompuneriior repetate) se ajunge la probleme care admit rezolvare imediatd. Evident, nu toate problemele pot fi rezolvate prin utilizarea acestel tehnici. Fara teama de a gresi, putem afirma c& numarul lor este relatlv mic, tocmai datori cerintel ca problema s8 admité o descompunere repetata, Divive ET IMPERA este o tehnicé ce admite 0 implementare recursiva. Am invatat principiul general prin care se elaboreaza algoritmii recursivi: ce se intampla la un nivel, se intampla la orice nivel (avand grijé si asigurém condijile de terminare). Tot aga, se elaboreaza un algoritm prin DIVibE ET IMPERA. La un anumit, nivel, avem doud posibiltati: 1) am ajuns la o problema care admite o rezolvare imediata, caz in care se rezolva gi se revine din apel (condifia de terminare); 2) nu am ajuns in situatia de la punotul 1, caz in care descompunem problema th dou sau mai multe subprobleme, pentru fiecare din ele reapeléim functia, ‘combina rezultatele gi revenim din apel, 3.2. Aplicatii 3.2.1, Valoarea maxima dintr-un vector GF Problema 3.1. Se citeste un vector cu m componente, numere naturale. Se cere sa se tipareasca valoarea maxima. 2. Problema de mai sus este binecunoscuta, Cum 0 rezolvém utilizéind tehnica DIVIDE ET IMPERA? Manual de informatica pentru clasa a XI-a 65 © Rezolvare. Trebuie tiparits valoarea maxima dintre numerele retinute In vector de fala J (initial, t=2 gi Pentru aceasta, procedam astte!: © dacd i=j, valoarea maxima va fi vil; © contrar, vorn parti vectorul tn dot vectori (primul vector va_contine componentele de la 4 la (444) @iv 2, al doilea va contine componentele de la (+3) div 2 + 11a J, rezolvm subproblemele (aflam maximul pentru fiecare din ele) iar solutia problemei va fi data de valoarea maxima dintre rezultatele celor doua subprobleme. Programul este urmatorul: Varianta Pascal Varianta C++ var viarray{1..10) of #include integer: Ant vi20) m2 n,itinteger Ant max(int dint 3) function max(i,j:integer) (int a/b; Hinteger; Af (143) return vEti else | bes: { aemax(i, (145) /2)7 demaxe( (+5) /244, 507 if (a>b) return a; else return by | benin , faremax(i, (+3) diy 2)7 > Dbeemaxe( (443) ay 262,397 if ab main() ‘then maxis (coutectnst; cimony else max for (int Snt;ieansiee) ona Ccoutcerynechcerd="; ond ein>>vthl > begin cout Jf, Algortmul prezentat este exclusiv didactic, in practic’ este preferat @algoritmul clasic. : : 62 66 Capitolul 3. Metoda Dimoe er Meera Manual de informatic& pentru clasa a Xi-a oe d proceaure intere 3.2.2. Sortarea prin interclasare i (pramiinteger; var a:vector); fiers : var bivector; delea; : isSeesintegers eked, GF Problema 3.2. Se consider’ vectorul a cu n componente numere tniregi (sau ce 3 ' reale). $8 se sortoze crescator, ullizénd sortarea prin interclasare. : Paee fa donee tga else : while (cen) and Gea) do { bod =ats; Interclasarea a dol vector a fost studi. Daca dispunem de doua girui de : if e{ileea(i] then jrony valori, primul cum elemente, al doilea cu n elemente, ambos sortate, atuncise pore eapat Speer oate obine un vector care confine toate valorile sortate. Algoritmul de interciasare disea; kreken Af (icom) este performant, pentru ca efectueaza cel mult men-2 compara, ' ond : else In cole ce umeazs, vom uliize algoritmul de interclasare tn vederea sori | begin sas ‘unui vector prin interclasare. ; Biel teats © Rezolvare, Aigoritmul de sortare prin interlas idee: pentru @ sorta un vector cu ‘n element Sortati, se interclaseaza. aro se bazeaz’ pe urmatoarea te fl impairim in dol vector! care, odata Conform strategie! generale Divine ET ImpeRA, problema este descompusa in oie ubprobleme de acelasl tp i, dupa rezolvarea lor, rezultatele se combina ({o particular se interclaseaza). Descompunerea unui vector in al dor secien care Sous Gt SoMali are loc pana c&nd avem de sortat vector’ de ure eau douai componente. {hn aplicatie, functia sore sorteaz’ un vector cu maximum doua elemento; Anterc inerciaseaza rezutatole; divimp implementeaza strategia genoreia metodel studiate. “Varianta Pascal farianta C++ tinclude type vectorsarray [1.,10] of integers ane Ant a(20}.ny var atvector; void sort (int p,int g, int af20)) procedure sort (p, grinteger; ares var atvector) ; int m 7 48 (atp)atal) var m:integer; ( mea(pl; begin p}=alal; if alpi>atal ‘then. » begin > misatp); alpit=ataly alai=ns void interc(int p,int g, int mint af20}) € amt BI101,4,3,4 iepy Jamel; kot) Jel; rsken ie dcem then for ji=i te m do bogin Dikl:salj}y keakea ond else for 4:53 bo @ do begin DO seaLi}y Keenkeed end; krety for limp to g do ‘begin ali} imbEe]) eeake, end ends procedure aivinp (pra: integerivar a:vector) wetasineeserr Begin SP laplcot then sort (p,<,8) ise Begin Brs(pea) av a7 aivinotpem a)? diving (medyara) 2 interetp,aima) Dy readinin); for irsi ton do begin . weite(at',d,+ Feadin(a{i}) end; ivinp(1.n, a); for i end. to n do writeln(alil) for (edi $ kel for (iepriceqsie+) Calidebods wekedy ) > vold aivinp (int p,int a, dnt afiol) {int my LE (g-p)a[5J, deci se inverseaza elementele afiate pe pozitile 2 $i 5, deci a= (2,9,3,1, 6) $i programul trece la modul de lucru ); 2,6,3)1,9) $i 80 revine la modul de lucru a); 4n2, $=d; a(2]>a{4], deci a=(2, 4,3, 6,9); se trece la modul de luoru b); 43, 324; {unciia. se inchele, elementul aflat inital pe pozitia 1 se giseste acum pe pozitia 4, toate elementole din stanga lui fling mai mici docat el, totodaté toate elementole din dreapta tui find mai mari decat el (k=4). Aliernanta modurilor de lucru se explicé prin faptul c& elementul care trebuie pozitionat se compara cu un element aflat in dreapta sau in stanga lui, coea ce impune o modificare corespunzatoare a indicilor & gi 3- J), Dupa eplicarea functiei woz, este evident 8 elomentul care se af nial tn @_pozitia 14 va ajunge pe o pozitie x si va raméne pe acea pozifie th cadrul vectorului deja soriat, fapt care reprezinta esenta algoritmului, Functia qurex are parametri 14 gi Le (limita inferioara gi limita superioara). in cadrul ei se utiizeazé metoda DwvIDE ET IMPERA, dupa cum ulmeaza: © se apeleaz poz; © seapeleaz’ gure pentru 14 gi k-1; © se apeleaz QUICK pentru k+1 sis. Varianta Pascal Varianta C++ type vectorsarray [1..100] of | #include Saeegers Ent at200)/n/47 Fi void poz (int 1d,int 18, inte var i,n,krinteger; Rosa taeisony eer {int tL, j=18,c,44=0, je-1; rocedure poz (1i,ls:integer; white (13) i var kiintegex; Cif (atloatsy) var arvector) ; ( ceatd]y aljleatily alil=c; e=ia; var i,3,¢,42,j:integer; Le-giy jee 70. it Capitolul 3. Metoda Dime er IMpERA we 4 ao void quick (int 14, int 1s) ( 4£ (tela Sf attueathi (poz (Li, 1e/k,a); ott quhok (14, 2) oe smile cee); ats} atta; y maia() {dnt iy cout<<"n=") cinson; for (isljicensite) Ceoutcenatnecdcer]un ein>satily eae ; 1 quick (1m); for (isijicenyise) cout<2, problema se complica. Not&m cu H(n, a,b,c) girul mutarilor celor n discuri de pe ta a pe tja b, utlizand ca tia intermediard, tia e. Conform strategiei Divine EF IMPERA, incerc&m s descompunem problema alte doud subprobleme de acelagl tip, urmand apoi combinarea solutilor. in acest sens, observim c& mutarea color a discuri de pe tija a.pe tija b, utlizaind ca ti intermediara tifa ¢, este echivalenta cu: mutarea an-1 discuri do pe tija a pe tia e, utlizénd ca ta intermediard tia By ~ mularea discului rimes pe tija b; , utlizdind ca ti it — mutarea an-1 discuri de pe tae pe termediar’ tae Parcurgerea color trei etape permite definirea recursiva a sirulul H(n, a,b,c) astfel: ab, nat M0200 ffa-sabhablle-tebel oot Ex: Privifl urmatoarele exemple: 41) pentru ne2, aver: #(2, a,b, o)=K(1,a,¢,b) ab, H(1,¢,b,a)=ac, ab, cb; 2) pentru n=3, ave: (3, a,b,c)=H(2,a,¢,/b), ab,H(2,c,b,a) #H(1,a,B, 6) ab, H(1,c,a,b),ch,H(1,a,b,c)=ab,ac,be, ab, 6a, cb, ab. H(1,b,c,a), 7 Capitolul 3. Metoda Diaoe er pena A ___________Capitol 3. metoda ormoe er | Varlanta Pascal Varlanta C++ var ayb,crchary include integer: char a,b,c; procedure han (niinteger; int ay a,b, erehar) tees cereal void han (int n,char a, 4€ nel then char b,char ¢) ‘weiteia(a,b} ) cout < > main() { cout< 3.2.5, Problema taieturilor DF Problema 3.5. Se da 0 bucata Greptunghiularé de tablé cu lungimea 2 si inaitimea b, avand pe suprafafa ei n giuri de coordonate numere intregi. Se care Sa se decupeze din ea o bucaia de arie maxima care nu prezinté gurl, Sunt Permise numa taieturi verticale si orizontale. © Rezolvare. Coordonatele gauriior sunt retinute in doi vectorl xv gi xv. Dreptunghiul initial, precum si dreptunghturile care apar in procesul taier sunt memorate in program prin coordenatele coltului din sténga-sus (x,¥), prin lungime $i inattime (x, 32). Pentru un dreptunghi (initial pornim cu toaté bucata de tabla), verificém daca avem sau nu o gaurd in el (se cauta practic prima din cole n gu). In sitvatia cand acesta prezinta o gaura, problema se descompune in alte patru probleme de acelas! tip. Daca bucata nu prezint& gurl, se compara aria ei cu aria unel alte Duca fara gauré, gasité in fazele precedente, Menjionam 8 dreptunghiul de aie maximal fara gauri este retinut prin ‘aceiag| parametri ca si dreptunghiul cu gaur, in zonele x. ve, Li, HF. {in concluzie, problema inifial& se descompune in alte patru probleme de acelesi tip, mai usoare, ntrucat fiecare nou dreptunghi are cel mutt n-1 gum, daca reptunghiu! initial avea m gauri. La aceasté problema compararea solutlior const jin retino dreptunghiul cu aria maxima dintre cele fara gurl 73 Manual de informatica pentru clasa a Xl-a Fie dreptunghiul cu 0 gauré: — xy 1 i, sc Pentru a se afla In interiorul dreptunghiului, gure trebuie sa indeplineas simultan conditile: 1) nev (4) >26, 2) xev (4) y) and tet erems then gaaktr true cise fisted #inciude int Lyhydyn,xfsy8 167 ne xv 120] ye (2017 | voia dimp (int x,int y/int 2, ine iy pte ety See VE, ince if, inte Re, Ine evti0n ine gv(201) inv genteedeiety : while (icsn && Igasit) TP lertiine ee vtsl dae Svlilsy ex yvtsl are) eatiests eee te wvtdyx next eth, mee ee Eb nema v0 wee ele ma o se NE LE MERCI)! 74 Capitolul 3, Metoda Diwoe er iupena Manual de informatica pentru clasa a XI-a 75, 1 gant eure | “peatn if (lemoiemne) ; 3.3. Fractali Amo (xy 2074-2, ieee ging OEE RE ay ifel? Fractali au fost introdugi tn anul 1975 prin luorarea revolutionaré a Cer tAd ys Peer fons matematicianului francez Benot Mandelbrot, "O teorle a serillor fractale", ce aap meee Meer ray | : teuneste totodata diversele teori dinaintea sa. El este cel care a inventat cuvéntul hae ie uclerent : Yractal’, de provenienta latina ("frangere’ — a sparge in fragmente neregulate). aime wt Tyaiyrrtll, | BAO : xiryf,1E/heseeys) Ccoutcctne#; cinsons Notlunea de fractal a aparut ca urmare a studlului viefii reale, tn care and for (int isi;icensiss) informatia geneticd continut® in nucleul unei celule se repetd la diferite scari oise { coub< (aeeney edo oay ti) } 4 transtorme fntr-o alta, format din mai multe figuri inifiale (de exemplu, linie Reni essay ee : fant) gi fiecare figura obfinuta s& se transforme In mod asemanator (aceste readin(n)? for drei ton do begin write (tt',4, I="); readin (xv til); write 'yE',4,*3=*); readin (yv(i}) end; write le"); readin (1); write(h="); readin (h) LE07 hEt=07 aimp(0,0,1,n,xf,E, LE, hE, sv ,y¥) + weiteln(x=')x£," yetyy£," ast/1f," het, he) > coutcrs"; cin>>1: cout<<"h="; cdn>>hy inp(0,0,2,n,x£,¥£,1£, hEyxvsyv) 7 cout<0 then area ‘epi wrivela(~rentativa esuatal” we ear; ont ond Constania detect are valoare a 0 $i Se specific? automata a driver-ului si a modului de tucru, 7 ” Sere Vom retine aceasta proceduré pentru c o vom utliza in exemplele ulterioare, 2) pin ncoarea cu ajtoru i primior dol paramett a unui civ tue Slctate de programator(n acest cae, muse posto oxenuta ogee un calculator ce nu este dotat cu placa grafica specificata): iaenileniN g@ariver := von; gmode t= VGART; initgraph (gériver, gnode, ' Af graphresult<0 then begin writoin(“Tentativa osuatat”); yates eal); ends ep \bgi) Tentativa de inifializare grafica poate e: sua din diverse motive, cur unitatii rava, calea indicat gest, ste. estore se reslzeara cu faneha inrocoa graphresult care retumeaza 0 fr mzephress in caz afirmativ gi o valoare diferita de 0, in Jp ovata inal ntl erat, nu e@ mal poate serie pe monitor, ca. pana write sau writeln). lesirea di : uilzaoa pocoduri clonegraphs MoM! Sate S© fa0e prin Manual de informatic& pentru clasa a Xl-a 3.3.1.2. Generalitati (varianta C++) bajul C++ (In varianta Borland), confine o serie de functii care permit realizarea unor aplicalii grafice. Acestea sunt reunite In figierul GRAPHICS H, ce Se gasoste in folderul zNCLUDE, Pentru ca o imagine s@ poaté aprea pe ecran, calculatorul utiizeaza placa Video, care difer’ in functie de memoria video $i alt! parametri, Pentru a accesa o placa’ video, trebuie s8 folosim anumite rutine speciale, specifice lor, numite Driver-e. Limbajul G++ detine 0 colectie de astfel de componente software si in functie de placa ce a fost detectata in sistem, se tncarcé un driver sau altul. Aceste figiere au extensia “bgi". Deoarece performantele componentelor hardware au depasit cu mult capacitatile CGA sau EGA, ne vom referi in continuare doar la driverul vea (Video Graphics Array), dezvoltat de firma IBM. Driver-ul VGA poate lucra in mai multe moduri, ins& vom prefera modul standard de inalta fozolutie “varnx" (constanta de tip intreg), ce poate afiga 640 x 480 puncte In 116 culo, Figierul ce contine driver-ul utiizat este "BGAVGA.car” Solectarea driver-ului gi a modului de lucru se face prin utiizarea functiei initgraph. Aceasta are trel parametri: gaxivex (de tip integer) care confine codul asociat driver-ulul, gmode (de tip antegex) care refine modul de lucru gi o vatiabila de tip string, care arata calea cétre unitatea GRAPH. Forma generala & acestel functii este initgraph (egériver, Egmode, "cale"); Primii doi parametti sunt transmigi prin referinf Iniiaizarea sistemulul grafic se poate face in dou’ felur: 41) prin a solicita s& se identifice automat placa graficd gi corespunzaitor ei s& se incarce un anumit driver gi s8 se selecteze modul de lucru ~ cel mai bun din punct de vedere al performantetor void init() ( géziver = DBTEcr; initeraph (egdeiver, agnode, “:\\BORLANDC\\BGI") 7 Af (grapnremule()) { coutce"rentativa nereusita."s coutce"apasa o tasta pentru & inchide...") getch(); exit (2); d y Constanta pmrEcr are valoarea 0 gi se specific’ functiei identificarea automat a driver-ului gi a modulul de lucru. ‘Vom retine funclia init () pentru ¢& o vom utiliza in exemplele ulterioare, 78 Capitolul 3. Metoda Dine er aren 2) prin indicarea cu ajutorul primilor doi parametri a unui driver si a unui mod de lucru solictate de programator (in acest caz, nu se poate executa programul pe un calculator ce nu este dotat cu placa grafica specificata): driver i= VOR; gnode := VaRHT) init graph (egdriver, ggnode, "E: \\BORLANDC\\B6r") ; 4 (graphresult ()) { cout ‘Tentativa de initializare graficd poate egua din diverse motive, cum ar fi lipsa uritafl GRAPHZCS, calea indicat gresit, etc. Testarea se realizeazé cu functia Iintreag’ graphresuit() care returneazé 0 In caz afirmativ si 0 valoare dlferita e 0, In caz contrar. Jf, Odata intrati in modul grafic, nu se mai poate scrie pe monitor ca pana acum (de exemplu, cu cout). lesirea din modul grafic se face prin utiizarea procedurii closegraph() Atenfle! Pentru a putea scrie si rula programe C++ ce utlizeazé modul grafic al \imbajului, trebule bifatd urmatoarea optiune, din meniu: Options / Linker / Librarles / Graphics library. 3.3.1.3, Setarea culorilor si procesul de desenare (Pascal si C-+-+) Cu siguranti, placa video utlizata de dvs. are performanie superioare Modului standard VGA, ce se regaseste In driver-ul limbajului Pascal sau C++, Pentru a generaliza insa, vom considera modul mentionat anterior, ce poate reda 26 culori, reprezentate pe 4 biti Fiecare culoare de bazé are atribuité 0 constanta de la 0 la 15, precum urmeaza: 0 ~ black (negru); 2 ~ blue (albastru); 2 - green (verde): 3 cyan (turooa2); 4 - xed (rogu); 5 ~ magenta (Violet); 6 ~ brown (maro); 7 — 1ightgzey (gti deschis); @ — darkgxey (ori Inchis); 9 ~ 1aghebiue (elbastru deschis); 10 ~ ghtgreen (verde deschis); 11 - 1ightcyan (lurcoaz deschis); 12 — lighted (fogu deschis); 13 ~ 1ightmagenta (violet deschis); 14 — yellow (gatben) si 25 - white (alb), Aceste culori sunt cele implicte, Pentru a utiliza mai multe culori (dar nu in acelas! timp), se poate schimba setul (paleta) de culori. intrucat in acest ‘Moment nu sunt necesare o multitudine de culori, nu vom prezenta in detaliu acest aspect, 79 Manual de informaticd pentru clasa a Xt-a > Pentru a seta culoarea de fundal, se utiizeaz& procedura (In Pascal) sau funetja (in C++) sotbkcolor (euloare) Exemple: setbkcolor(6); Sau setbkcolor (RED) 5 > — Solectarea culorii cu care se deseneaza se face cu ajutorul procedurii (in Pascal) sau functiei (In C++) setcolor(culoare) +. Exemplu: setcolor (15); sa setcolor (WHITE) +. Observatii ‘Schimbarea culorii nu afecteaz’ ce am desenat anterior, ci doar ce este scris dup’ apelul acestei rutine, ¥ in cazul limbajului C++, numele simbolic al culorii se scrie obligatoriu cu majuscule, Operatia de desenare c 8 printr-un pixel de Oricare ar fi modul de lucru ales, un punct se reprezinta p ° coordomate x (ini) $i (coloana), ambele valor ntregl. Punctul din sténga rus are cvordonatele (0,0). Pentru a ne muta fa poziia xe), vom Foo brocodura Ch a Pascal) sau functia (in C+#) moveto(r,y). Pentru tu cet. determinat anterior, pand la © nous poziie, vom utliza procedura (in Pascal) sau functia (in C++) 1ineto(x1,y1}. Astfel, vom obtine © lini punctele de coordonate (x,y) $i (text). linie pe diagonala Iu, Mai jos, este prezentat un program ce deseneaz’ o ‘ principal ecru (da Ta coll din stnga-us la cotl din dreapta js} Varianta Pascal bog: main () begin init 07 setoctor (rea) « Jotcston (2D) moveto(0, 007 soret0(0,0)) iM Tinete (getmace, getmea) Tineto (getmarce() , goemang (007 readin) getehO ona. , emasry (0 De asemenea, doud functi foarte utile sunt getmasce gi ge Pascal) sau getmasce() § gotmaxy‘) (In C4), Acestea inorevaloerea minima pec, maxima a coordoneteor de pe ecran. Aste, cu autorun: se poate Sbtine o independenta relativa a progremelor fal de modul grafic al sistemul 80 Capitolul 3. Metoda Dive cr imPena 3.3.2, Curba lui Koch pentru un triunghi echilateral Se considera un triunghi echilateral, Fiecare laturai a sa se transforma aga cum se vede in figura urmatoare (se imparte In trei segmente congruente, se elimina segmentul din mijoc si se construieste deasupra un triunghi echilateral}: ee Figura 3.1. Exernplu de transformaro Fiecare latura a acestul poligon se transforma din nou, dupa aceeasi reguls Sa se vizualizeze figura obtinuté dupa 1.8 pasi (numar cit de la tastatura) J, Aceasté curba este cunoscuta tn iteratura de specialitate ca fiind curba lul ‘@” Koch (Herge von Koch a fost matematician suedez si a imaginat aceasts curb in anul 1904), Programul principal va apela, pentru fiecare segment care constitule o latura a trlunghiului, 0 procedura numita generator, Aceasta executa transtormarea de is ofl, avand ca parametri de intrate coordonatele punctelor care constitule exiremitatile segmentului, numarul de transformari facute (m) si numarul de transformari care trebuie efectuate (28). Pentru a injelege functionarea proceduri, trebuie s& avem un minimum de cunostinte specifice geometriei analitice (ce se poate face fara matematica?). Fie AB un segment de dreapta, unde A este un punct de coordonate (x,y), lar B are coordonatele (xz,y2). Dou’ puncte P; gi P, impart segmentul intron anumit raport, notat cu &: ack yb ee? PE 2, Demonstrati singuri aceste formule! Fig sogmentul AB cu A(x:.y:) $i B(Xa,e). Considerim punetele C si D care ‘impart segmentul th trei segmente congruente. ‘Afiém coordonata punctulul D: DA DB a t2-x, ytd ys 3 3 Problema consté in stabilirea coordonatelorvarfului noului echilateral. Acestea se obfin dec’ se roteste punctul © in jurul Unghiul 2/3. Rotatia 0 efectueaza procedura rotplan, triunghi punctului D cu 81 Manual de informatici pentru clasa a xI-a 88 prezentém algoritmul care sté la baza procedurii genexatox: 1 AB, + se pomeste de la segmentul AB; «se determiné coordonatele punctului care constituie varful trunghiuiui echiateral (s&-1 netm cu V); ‘© in-cazul in care segmentul nu a fost transformat de 1e or, se apeleaza generator pentru segmentele AC, CV, VD si DB; + contrar, se apeleaz’ procedura care traseaza linia franté ACVDB. in programul principal au fost alese punctele care determing tiunghul ectilateral infil ~ plasat in contrul ecranuli = i pentru fecare, segment ce constituie 0 latura @ acestuia s-a apelat procedura generator cura, se coloreaza interiorul acesteia Programul este urmatorul: Varianta Pascal “Varianta C++ uses graph, crty var L,gariver, gnode, Issinteger; smnax, ymsx:integer procedure initgy rovedure xotylan (xc, Pyirinteger? var x,yrinteger; Saghtsseeny wean SEE round (xe ete) * ‘cos (anghi)=twieve)* atone) yen found (yes etx) ™ ein anant)s(rcve)® Gontunghi) ons procedure desenes (it ¥132, YaysSysintouer) 7 Ppoveto(xt,yi) 7 Tinetot(atdeaa) iv 3, Gryieya) atv 3; dineto (3,93) Lnetot(adearaa) aly 3, (qusaeya) div 3), aineto(etsy2)7 ond procedure Sonerator (xt, ¥1,32,¥2, Relesineeges) > ‘yar x yineeger: include “graphica.n" #include include #include Winelude Ant gdziver,gmode, 18,17 void init() Cod void rotplan(int xc,int ye, int x1, dnt yl,int ex, int ay, float unghi) cold (nce (xtc) Seon (unght)- (yi-ye)*sin(unghi)); ¥ = coil (yer (xd-xe) Ysin(unghi) + (y1-ye) *eos (unghi))7 oe , void dosones (int seine yy fae aarant y2,ane i, ine ¥3) oweco(ad3); : ‘Lineto(div( (2*:1+2),3) quot, aiv((aeyieya) 2) ano) nec Ge93) 1 Lncve (diel Gcieaea) 2) uot, Sh (ytezeya) 3) ane) uinssoa.ynr abr peneeene yer ee 82 Capitolul 3. Metoda Dimoe er murena Bashi Fotplan( (2rxieaa) diy 3, (hetra) aie Gata) as 7 Gededeya) aie Seay bd if nte; anit); setcolor(6); L = gotmasce()~320; generator (160, gatmaxy()-250, 160+L,getmaxy()~150,1,18)7 generator (160+5, getmany()~ 150, 260-div (1,2) .quot, sgotnany()~150- coil (2 (sqrt (3)/2)),2,28); generator (160+div(t,2) -quot, ‘getmaxy ()~150- coil (1 (agrt (3) /2)),160, setmany()=150,1,1a)7 sevsilistyie(1,4)7 Elood#it2 (div (getmasee() ,2) squot , div (getmarce(), 2) quot, 6)7 getoh()s ) Stomeneanb 07 Priv mai jos rezuttatele obfinute pentru diferte valor ale ui Le: *k* Is = 2 le =3 ls =4 Figura 8.2, Exemple de fractal forma cu sjutorl curbel lui Koch (unghi ecilatral) Manual de informatic& pentru clasa a XI-a 83 3.3.3. Curba lui Koch pentru un patrat Se considera un patrat. Flecare laturd a sa se transforma dupa cum se vede in figura de mei jos: LJ Figura 8:3, Exemplu de ransformare Fiecare segment al liniei frante astfel formate se transforma din nou dupa aceeasi regula. Se cere si se vizualizeze curba dupa 1s transforméri (valoare cits de la tastaturé), Transformarea gi desenarea unui segment sunt realizate de procedura dasen, Aceasta are ca parametri de intrare coordonatele punctulul care determind segmentul, numarul de transformari efectuate (a) si numérul de transformari cerut (1.8). Procedura contine urmatorul algorit: + dacd nu a fost efectuat num@rul de transformari_necesar, se calculeazé coordonatele punctelor care determina linia franta obtinuta pomind de la segment si pentru fiecare segment din aceasta line se reapeleazé procedura desen; * contrar, se deseneazé linia franta obfinut’ In final, figura se coloreaz’. Programul este prezentat in continuare: Varianta Pascal Varianta C++ uses graph,crty | var gaziver, gnode, Le:integer: procedure inita procedure rotplan(...)7 procedure desen (xl, ¥1,22, y2)n,1stinteger) var ¥3/206, 5 6,270, 38C, ¥3.¥4.¥5,¥6,¥7,v8,yorinteger: begin if neele then begin H3 1 (3txeLtne2) Av 4 y3ie(3*yleya) div 4; rotplan(x3,y3 21/1, x4,¥4, =ph/2)i xers(eitn2) div 2s | voila inie() include "graphics.n" #include #include include include int gdriver,gnode, 16,17 void desen(int st1,int yi, int 32,int y2,int aint 1a) {int 53,204, 45, 6,078, xo,y3, v4,v5,¥6,¥7-¥8,¥er Af (necle) { wGediv (3 "eL432,4) «quot: yaediv(3*yley2, 4) quot; xotplan (x3, 3,34, 74,204,746, mMPE/2)7 84 Capitolul 3. Metoda Divine er IMpena yore Winya) div 37 rotplan (xe, ye, 33 /¥3,85/¥8, -pilaii rotplan (xe, Yo, 33,73, 28,¥6/Di/2); se (aite3xa) aly 47 yOro(yie3ey2) div 4; rotplan (x8 ,y8,x0,¥6,%7,¥7, pi/2); oven (xi -y1,%3/y3 ned ,18); Gosen (x3, y3;x4,y4, a1, 18) 7 donon (x4, y4,x5,¥5,n+1, 18) 7 desen (x5,¥5,xc,ye,ne4, 18) ; dosen (xc, ¥e,x6,y6,n+1,18)7 doaon(x6,y6,x7,y7,n+1,18) 7 dasen(x7,y7,x8,y8,n+1,18); degen (x8, ¥8,x2,y2,n+1,18)7 if n= 16 then begin moveto(ad,y1) 3 Lineto (x3,¥3)7 Lineto(n4sya); Lineto(x8,¥5) 7 Lineto(x6,¥6) 2 Lineto(x7,¥7)7 Lineto(x8,¥8); Lineto(se2,¥2)7 and ona fonds begin write(*1s= '); readin (is); initg; setcolor (red); dozen (100, 100, 300, 100,1,18); | desen (300,100, 300, 300,1, 14); esen (300, 300, 100,300, 1,18) ; desen (100, 300, 100,100,126) setfillstyie(i, blue): Flood#ill (getmasxe div 2, getmaxy div 2, xed); BERG GLE, 2) cause yordiv(ylty2,2) .quot; rotplan (x0, ye,x3,y3, 25,95, mele /2)7 rotplan (xc,¥e133 /¥3,26,¥6, M_BI/3); uBadiv(x143*H2, 4) -quot; yOadiv(yi+3*yz,4) .quot; votplan(x8,y8,x6,¥e,27.¥7, | M_PI/2); oven (xh, y,x3,y3,neL, 18); doven(3,¥3,x4,y4,n+2,10)7 owen (xd, y4,x5,¥5,n+2,10)7 doson(x5,y5,x0,yo,n+1,19)7 desen (xc, ye,x6,y6,n+1, 18 dogon(x6,¥6,x7;¥7,n+1,18) 7 dosen(x7,y7,x8,y8,n+1, 1a) owen (x8, y8,x2,y2,n+1, 18) 7 if (a =='1s) (Cmovato (xy); Lineto(s3,¥3)7 Lineto(eds ¥4)7 Lineto (5, ¥5) 7 Lineto (x6, ¥6) ; Lineto(e7/¥7) 7 Lineto(x8, v8) 7 Linevo(xa,y2); > d > nain() (coutc<"1es "; cins>te: init(); setcolor(6); desen (100, 100,300,100, 1,18) ; dozen (300,100, 300,300,1,18); desen(300, 300,100, 300,1,18)7 desen(100, 300, 100,100,1,18); set filistyie(1,3)? Elood#ill (div (getmaree() ,2) sauot, div (getmaxy() ,2) «quot, 6) 2 getch(); closegraph(); Sunt prezentate mai jos imaginile obtinute in urma rutin programului, pentru diferite valori ale lul 12: He deen dee2 ate Figura 3.4, Exemple de fractal format cu sjutoruleurbei lui Koch (pirat) Manual de informatic’ pentru clasa.a Ina 85 3.3.4, Arborele Se da un segment AB, Cu ajutorul lui se construieste un arbore, aga cum se vede in figura de mai jos: Figura 3.5, Exemplude transformare in cazul unui arbore Lungimea fiecarei remuri este 0 treime din lungimea inital a segmentulul Flecare latura se transforma in mod asemanator, Se cere s& se vizualizeze figura astfel rezultata, dupa 18 transforma Pentru obfinerea ramurilor se procedeaza astfe!: © se considerd punctul situat pe dreapta determinata de segment si pentru care avern: peQhay, x The 2 oe eo 3 2 «se roteste acest punet in jurul punctului B(x.,y2) cu un ungt ‘© se roteste punctul in jurul lui B cu unghlul —/4 In urma acestor rotafii se obtin coordonatele punetelor care, Impreund cu punctul B, determina segmentele ce costituie ramurile arborelut Proceduta desenez are ca parametti de intrare coordonatele unui segment, numarul de transformari efectuate (n) si numérul de transformari care treouie ‘efectuate (18). in cazul in care nu s-au efectuat toate transformatile, se traseaza segmentul (cu 0 culoare oarecare), se calculeaz coordonatele punctelor care determina ramurile si, pentru fiecare segment, se reapeleaza procadura Programul este prezentat mai jos: Varianta Pascal Varianta C++ include “graphica.n" include #include finclude #Hinelude int gariver, gmode, 18, uses graph, crt; var gdriver, gmode,1s:integer yonaxt, ymax integer? procedure initas 86. Capitolul 3. Metoda Divioe er t4PeRA, Procedure xotplan (xe, 76,21, yiinteger; var st,y:integex; unghi:zea1); procedure desenez(xl,y1,12,¥2, ‘a, Letinteger) ; var x,ysinteger; begin Lf neele then begin secolor (1+zandom(15)) 7 movato (xt, yi) 7 Lineto(x2,y2); Fotplan(x2,y2, (3¢x2-x1) div 2, (Qty2-yl) div 2,x,y,pi/4)7 desenez (x2, y2,2,y,n+1, 18) 7 rotplan(x2,y2, (342-21) div 2, (3¢ya~yi) Biv 2,3,¥,-pi/A); asonox (x2, ¥2,x/y/n41,18)7 ena ena; begin desenez(gotmasct div 2, gotmaxy, getman div 2, gotmaxy-250,1,18); readin end. void inie() teed vold rotplan(...) Cred void desenez (int sxisint yi, int x2,int y2,int n,int Je) (int xy Lf (nels) { setcolor (1+random(15)) 7 moveto (xi ,y3) 7 Lineto(x2,¥2); rotplan (x2, ¥2, div (3*x2- wel, 2) quot, div (3*y2-yi,2) HOES Ye _PI/4) 7 dasonex (42, ¥2,%/¥ 02,10) 1 rotplan(x2,y2, div (3¥2- ui, 2) .quot, div(34y2-y1, 2) quot, ¥,-M_PT/4); ) Saenee Gee va wey met, 10) d main() { randomize(); cout<<"ax "7 oins>ies init (); setcolor(6) 7 dosonez (div (getmasse() ,2) quot, gatmaxy(), div (gotmuce(),2) quot, getmaxy()-250,1,18) 7 etch); » ctoneeeant: Pentru diverse valori ale parametrulul de intrare 11s, vom obtine arbor ls = 3 Pe le =5 ls =7 Figura 3.6. Exemple de iracta de tp arbore : : Manual de informatic& pentru clasa a Xi-a 87 [ observatii ¥ —_Exemplele grafice prezentate au fost generate pentru valori mici ale lui 1a deoarece la Upairire, detalille sunt greu de observat peste o anumita limit Y — Generarea fractalilor reprezint& 0 aplicatie @ reoursivitéfi, tehnica aplicaté {lind Divibe ET ImPERA. Pentru valori mari ale lui 1s, timpul de efectuare al calcutelor poate fi gi de ordinul zecilor de secunde, cea ce poate fi considerat un inconvenient major. Probleme propuse 1, Seciteste az1, numar real, Se cere s& se scrie o functie care calculeazé 1n(a) ‘cu 3 zecimale exacte, Nu este permis’ utlizarea functiei logaritmice a limbajulul 2, Soriati o functie care calculeaza prin metoda Divive er IMPERA suma numerelor refinute dintr-un vector. 3. Referitor la problema anterioar’: care este complexitatea algoritmului folosit? Se va considera ca operalie de baz adunerea, 4. Se citeste un numér real xe (-10000, 10000). S& se afigeze partea fractionara, Exemple: pentru x=2.23, se va afiga: 0.23; pentru s=-12.7, S@ Va atiga 0,7. Nu se vor folosi functii specializate ale limbajulu 5. Se stie c& ecuatia xe°+2e-1=0 are o singura rédacind real in intervalul (0,1). Sorieti un program, care 0 afiseazA cu 4 zecimale exacte. 6. Problema selectiel. Se considera un vector cu m componente numere naturale si Astsn, Se cere 8 se determine at t-lea cel mal mic element. Imaginati o ezolvare care utiizeaza functia Pox de la sortarea rapids! 7, Se considera un vector care refine n numere naturale. Se cere sé se determine daca exista un element majoritar (adic& un numar care se gasegte in mai mult de |n2}+1 elemente) Victor Mitrana 8, Fiind dat x real, s& se calouleze ['/2r| ou patru zecimate exacte! Nu se vor folosi func spectalizate ale imbajulul 9. Se pleaca de fa un patrat a cdrui suprafajé se divide in 9 parti egale prin Impartirea fiecdrei laturi in 3 p&rfi egele. Patratul din mic se elimina. Cu patratele ramase se procedeaza la fel. Vizualizeli figura dup& 1a astlel de transformer (Covorut iui Sierpinsk). 88. Raspunsuri 1. In(a)sx © azo* © o%-an0. Daci rezolvaté ecuatia £(x)=0, Aven £0: Capitolul 3. Metoda ioe er Iaeena, ‘A nolm cu £(sx)=e*-a, alunci trebuie ‘L-a<0 i £(a)me"-a>0. De aici, rezulté c £(x) are o radacina in intervalul (0,2). Cum £(x) este strict crescétoare (ca diferent’ intre functia strict crescatoare ©” si o constant), fadécina este unic&. Algoritmul pe care il folosim se numeste in matematicd "metode injumetatini intervalulu’, dar, din metodei DIVIDE ET InPERA. Fle 1420 si lesa, m= (a+b) /2, Daca £ (14) x8 (m) <0, rddacina se gaseste unct de vedere informatic, corespunde in (24,m), alffel rSdécina este in tm,28). Conditia de terminare este ca lii-ts]<0.0001, pentru ca trebuie s& avem 3 zecimale exacte, Varlanta Pascal Varianta Cr+ var a:real; include function LogN(a,ii,le:doubie): | fmelude double double ay ee double LogN(double «,double 1i, if a=l then LogN:=0 Seuene ae} aa (4€ (asst) retuxn 0; if abo(1i-20) <0. 0001 bread cheat esguie aint ia 4f (fabs (1i-1e) <0.0001) aise return (1is1s)/2; SE (oxp(2i)-a)* a 7 (oxp((1+18) /2)-a) <0 Hatt ieee Gay eant thon (exp ( (1it1s) /2)-a) <0) LogN:=LouN(a, 14, (ide) /2) ee ents else (isis) /2); ogN:=LogN(a, (14418) /2,18) etse return LogN(a, eae ; (2iels) 2,18); begin main() write (‘as'); readin(a); Ccoutecan"; oin>ray writeln(’ regultat caloulat:*, LouN(a,0,a) 13:3); weriteln(' rezultat preluat ', ana) :3:3)7 ona. > cout<<"rezultat calculat <>n; write(*ns*); readin(n)s for (let;icen;i++) for i:s1 to n do readin(v[i}); ‘elay>v i wriveln (suma(i,n))5 end. cout <x, elementul cdutat are indicele Intre +2 gi le gi reluam rularea functiei Fox Intre aceste limite, Datorita faptulul c&, la fiecare pas, se restrange numarul valorilor de cautare, se ajunge in situatia tn care t=k. Secventa este: f Varianta Pascal VariantaC++ JL, Practic, la fiecare pas se injumatateste intervalul in care se cauta solutia gi ‘#” aceasta corespunde strategiei generale DIviDe ET IMPERA. 2, Programul este prezentat mai jos: \Varlanta Pascal A Varianta C++ #include int n,i,v(i017 type vectormarray{t..9] of integer, var vivector; ay isinteger Listy lesny a0. { poz(li,1s, ka): if (eck) Leek-2; Af (tok) Lisked; | atsety assem; | repeat | poz (2i,is,k,a) | de tek chen 1: | Af tok thon Lirmkra; | untin tex; Ywhite (tsk); [writein(‘mlementul cautat *, | cout< — Metoda backtracking are la baz un principiu simpiu: daca in procesul de generare a unui vecior solufie Sica, « . «2, pentru componenta ke, atunci ‘cand am generat deja sea, « «3, Constatém ca valoarea x, nu este bine aleasa (pastrand-o nu se va ajunge la o solutie), nu trecem componenta +1. i relum céutarea pentru alta valoare pentru componenta x, iar dac& aceasta valoare nu exista, reluém cautarea pentru componenta kt. h ‘Observati faptul c& dupa ce am analizat posibilele valori pe care le poate lua ‘componenta ie, avem doua posibiltat: ori tecem la componenta ke+1. (facem pasul inainte), ori mergem la componenta k-4 (tacem pasul inapol). Trecem la exempificarea algoritmulul pentru generarea permutarilor, tn azul in care n=3. * — Componenta 2 va _memora numarul 4. Intrucét existé P> permutari care incep cu 4, trecem la elementul 2 - face pasul inainte. * Componenta 2 va memora numarul 1 aja + Nu exista permutari care Ineep cu 3,4, motiv pentru care, [7 pentru ageeasi component’, vom refine valoarea urmatoare, adic& 2, Intrucdt exist& permutiri care Incep cu 1,2, vom trece la elementul 3 (inainte), * — Componenta 3 va memora numarul 2. 212 z . re sunt de forma 4,2,2, moti Nu exista permutéri care sunt de forma mat pentu TTT a] 2]3 care aceeagi componentd va retine numarul urmator, 2. . Nu exist permutari care sunt de forma 1,2,2, motiv pentru care aceeasi componenta va memora numérul urmator, adica 3. Am obtinut deja o prima solute gio afigam: 1 92 Capitolul 4. Metoda backtrackin * Pentru componenta 3, nui exist 0 alt valoare pe care o TT putem utiliza, Din acest motiv, vom trece la elementul 2, ELE] {Inapoi). Componenta 2 are deja memorata valoarea 2. Alegem valoarea urmaitoare, 3. Intrucat existé permutri care Incep cu 4,3, vom trece le elementul urmator, 3 (inainte). TEE] «Prima valoare care poate fi memoraté este 4. Intrucat nu exist& permutéri de forma 1,3,2 trecem la valoarea urmatoare 2. Dar 1,3, 2 este solute gio afigaim, + Aigoritmul continua pandi cand se ajunge la componenta de indice o. in acel moment, au fost deja afigate toate permutarite, 2 Exercifiu. Aratati cum functioneaz& algoritmul pana se ajunge la ‘componenta de indice 0. 4.1.3. O modalitate de implementare a metodei backtracking Pentru ugurarea infelegerii metodei, mai intéi' vom prezenta un subpprogram general, aplicabil oricarei probleme. Subprogramul va apela alte subprograme care au intotdeauna acelasi nume si parametti si care, din punct de vedere al metodei, realizeaza acelasi Iucru. Sarcina celui care face programul este sa scrie explicit, pentru fiecare problema in parte, subprogramele apelate de acesta ¥ Evident, 0 astfel de abordare conduce fa programe cu multe instructiuni. Din acest motiv, dupa Infelegerea metodei backtracking, vor renunfa la aceasté forma standardizata. Dar, principiul ramane nemodificat, ati subprogramul care implementeazd metoda. El va fi apelat prin back(1). “Varlanta Pa Varianta C++ procedure back(k:integer); begin LE golutie(k) ‘chon tipar oui begin inbt (ie), while guccesor(k) do Af valid(k) then back(k+1) ond ona; void back(int ) « Lf (solutie(k)) tipar(); else (Anie(e; while (succesox (X) ) i (valia()) back(Ke1)) : 93 ‘Sé-l analizim! Subprogramul are parametrul ie de tip intreg. Acest parametru are semnificatia de indice al componentel vectorulul pentru care se cauta o vaioare eonvenabila, Algoritmul va porni cu componente de indice 1. Din acest motiv, subprogramul se va apela cu back(1), Dup& cum observatj, subprogramul este recursiv, > Iniat se testeazé daca s-a generat o solutie, Pentru aceasta, se apeleazd subprogramul solutie (Kk). Pentru permutar, vom avea o solutie cand s-a generat 0 secventa alcatuit’ din n umere distincte. Cum subprogramul este recursiv, acest fapt se Intampla atunci nd 8-2 ajuns pe nivelul ne2. > — Dacd s-a obtinut o solutie, aceasta se afigeaz’. Pentru aceasti operatic se va utiliza subprogremul tipar. > In situatia in care nu a fost obtinutd o solutie, se initializeaz& nivelul x. Inifalzarea se face cu valoares alata tnaintea tuturor valorilor posibile. Se va folosi subprogramul init. Pentru permutér,iniializarea se face cu 0. > — Dupa iniializare, se genereazé, pe rand, toate valorile multimil a, Pentru aceasta se utilizeaz’ subprogramul euccesor. Rolul sau este de a atribui ‘componentel k valoarea urmétoare celel deja existente, > Pentru fiecare valoare generaté, se testeazé dacd aceasta indeplineste anumite conditii de continuare. Acest test este realizat de subprogramul va1ia: > in cazul in care condifiile sunt indoplinite, se trece la componenta ka, urmand ca generarea valorilor pe nivelul i s& continue atunci cand se revine pe acest nivel; ware nu sunt indeplinite, se genereaza urmatoarea valoare pentru componenta k. > — Dupa ce au fost generate toate valorile multimil a, se trece, implicit, la componenta 4, iar algoritmul se incheie cfind k=0. Pentru permutari, pe fiecare nivel, valorile posibile sunt Av(2,2,.../m). Conditia de continuare, in acest caz este ca valoarea aflati pe nivelul 88 fie distinct In raport cu valorile atlate pe nivelurile inferioare. Programul de generare a permutérllor este prezentat in continuare. Varianta C+ bogin function succesor (k:intager) rbooleans begin if soltk) ratii tis readin(n) ; aj) (id=atiy (312 for diel to n do ? for j:=1 to 4-1 do back(2); begin ’ write(alt,i,t.t,5," voadin(ali, ji); alj/4r=a(, 3) end; pack (1) end. Manual de informatica pentru clasa a Xia 103 2 Exercifii 1. Solutia afigata este gi solutia care utilizeazé un numair minim de culori? 2. Daca tarile din centrul figurii alaturate sunt numerotate cud, 2, 3, 4, lar cele de la exterior cu 5 $i 6, care este solufia afigaté de programul dat? Este acesta numarul minim de culori necesare? Sr, Figura 4.8, Cate culori sunt suficiente pentru colorarea unei hart particulare in care orice fara se invecineaza cu cel mult douss ari? 4. Dati exemplu de particularitate pe care poate sa o aibé o harta pentru a fi suficiente doua culori pentru colorarea tuturor tailor? 4.4. Aplicatii ale metodei backtracking in combinatorica 4.4.1, O generalizare utila ‘Acum, c& am Invatat s& generdim permutérile mulfinil (4,2. . «n>, se pune problema s4 vedem de ce este ull acest algoritm. La ce foloseste faptul ca putem aranja numerele (1,2. .n} in toate module posibile? Sa observim c& acest algoritm poate fi folosit pentru a aranja oricare n elemente distincte in toate modurile posibile. & 1. Se da o mulfime alcétuité din a litere distinte. Se cer toate cuvintele care se pot forma cu ele, astfel incat flecare cuvant sé confiné n litere distincte. De exemplu, dacd muljimea este (a,b,e}, vom avea cuvintele: abe, ack, bac, bea, cab si cba. Exemple 2. Se dau numele a n persoane. Se cere sa se afigeze toate modurile posible in care acestea se pot ageza pe o banca. De exemplu, daca n=3, lar persoanele sunt Toana, Costel gitihaeza, atunci solutile sunt Toana Costel Mihaela; Toana Mihaela Costel; Costel Ioana Mihaela; 104 Capitolul 4, Metoda backtracking in asttel de cazuri, cele n elemente distincte se memoreaza intr-un vector v, aga cum vedeti mai jos: =P] Toone aihacia] Atunci cand s-a generat 0 permutare, de exemplu 213, vom afisa VI2]VIL1VI3], adicd bac, in primul caz sau Costel Toana Mihaela, in al doilea caz. Procedeul de mai sus poate fi folosit pentru oricare alta aplicatie din combinatoric&, in probleme cum ar fi: generarea tuturor submultimilor unei multimi, generarea aranjamentelor, a combinarilor sau a tuturor partilor unel multim rl Exercitiu, Scrieti programul care rezolva exemplul 2. J] Motimea permutirior multimit ¢2,2,...m) reprezinté toate functile @ bijective £:(1,2,...,n}(4,2,...m). De exemplu, dac& n=3, permutarea 213 este functia £:(1,2,3)3(2,2,3) definita astfel: £(2)=2; £(2)=4; £(3)=3. 4.4.2. Produs cartezian © Enung. Se dau nm multimi: Ay Raye Boy UNDO Aya {1, 2, +6/i}, pentru ke1,2,.++/n. Se cere produsul cartezian al celor n mul Exemplu: ay=(1,2), Aoe(2,2,3), Bs=(4, 2/3 ROADS (Le LL), (Lee Bo (e043) ¢ (Le 204) o (142, 2) (1/243), (4,364) 5 (4, 3,2) 5 (1, 3,3) (Zp De) y (2p 2,2) (24143) 4 (24242), (2,242), (2,23) 4 (2/34), (2,342), (243,3))- WZ Rezolvare. De la inceput observam ca este necesar sa afigm toate solutile, SB observim c& 0 solufie este de forma x1, 3t2r + +43, CU ERs, 26R2, aE%y, De aici rezulta necesitatea folosiri unui vector sol, cum componente, unde 01 {1] va confine numerele naturale intte 1 si ks, 801 [2] va confine numerele naturale intre 2 gi, .., 801 [2] Va confine numerele naturale intre 1. gi eq. Observimm c& valorile care pot filuate sol [1] sunt intre 4 gi tx, valorie care potfiluate sol f2} sunt intre 1 sit, ., valotile care pot fi luate sot fa} sunt intre 1 Si ky. Pentru a putea refine aceste valori, vom utiiza un vector a, cu n componente, unde afi]= ki, af2]= a, aln]= ke. Pentru exempiul dat, vectorul a va refine (2,3,3) Important! S& observim c& orice valoare retinuté de sol{i] intre 4 gi ky indeplineste condifile de continuare (este valida), Din acest motiv, nu mai este necesar 8a utlizam subprogramul valid Manual de informatica pentru clasa.a Xa zs 105 Mai jos, puteti observa programul care genereaza produsul curtozian al muttimilor date: Varianta C++. ‘Varianta Pascal include Ant ny gol (10},af10), void back(int i) var n,isinteger: gol,araxray[1..10) of at Cf c=ned) procedure back(k:integex) { for (ietsicensiee) bogin cout < begin ° for i:c1 ton do { got th) 207 ‘eeite (sol (11) ‘while (gol Uc) end > > else begin main() ‘ cout <<*Munarul de multimi="; eimons for(int detsi ww doliarenytis 10) of fae ay soi (20) et integer? void back(int ) rocedure back (Ksinteger) ; CAE (eesned) Begin (for (laisicensite) Af kenel then cout< webte (sol [i)) 7 oe, get weitela sol Tk] =-27 ea while (sol [k) while sol {k) ‘01 [k) ren02 tk] +15 paint) ; bo-pauesit { cout<4, 801 [De] >aol [k=] Manual de informatici pentru clasa a Xa b) Pentru flecare ke (2,2, 109 p), solfklsn~p+k, S3 presupunem, prin absurd, cA aceasta ultima relatie nu este respectata, Aceasta inseamna c& 3, astfel ineat sol (k] >n-prk. Dect sol [+i] >n-pek+2, s01 [p] >n-ptp=n. Absurd, De alli rezult ca Lssol [1] Sn-p+1, go [1] >s gout>D? back (1) 2 J ®xeminénd rayonamentul propus putem observa od, In anumite cazur # analiza unei probleme conduce la un algoritm cu mult mai rapid. no, Capitolul 4. Metoda backtracking 1. Se dau coordonatele din plan @ n puncte. Afigati coordonatele varfurilor tuturor patratelor care au ca varfuri puncte din multimea considerate, 2. Se dau n substante chimice, Se tle c&, in anumite condiji, unele substanfe intra reactii chimice cu altele. Fiind date » perechi de forma (4,3) cu semnificatia ca substana 4 intrd In reactie cu substanta 3, se cer toate grupurile de s tebUIe 8A fie distincte. ‘Spre deosebire de algoritmul de generare a combindiilor, aici ne intereseaza toate permutérile unei solutii(acestea sunt, la randul lor, alte soluti). Aceasta inseamné ‘cd nu mai putem pune in solutie elementele in ordine crescditoare, Sa recapitukim: - 0 solutie are p numere din B; = numerele trebulie sa fie distincte, Rezuita de aici o8 algoritmul este acelasi de la permutéri, diferenta find data de feptul cd solutia are p numore, nu n ca in cazul permutatilor. Manual de informatica pentru clasa a XI-a Ww Varianta C++ \Varianta Pascal Hinclude int n,p, sol [1017 Ant valid(int k) {for (int ietpiceds+) 4 (soL [k] seo (41) return 0; return ty > yold back (int ) (Cant i7 if (et=ped) ( for (Jetsicmpsie+) ‘cout < begin else wack (+1) Scene: ond; bogin readin(n)1 readin (p)s ack (2) ond. 2 exert 1. Se citese m, p $i apol n litere distincte. Afigati toate cuvintele care se pot forma, cup dintre ele. 2. Se citesc n gi apoi numele mici am persoane. Stiind c& toate numele care se termind cu a reprezint’ nume de fat, celelalte find nume de baieti, s@ se afigeze toate mulfimile de perechi fata-baiat care se pot forma. Dou multimi sunt distinete daca cel putin una dintre perechi diferd. De exemplu, pentru n=5, maria, Ana, Doina, Doru, Cosmin, se afigeazé multimile: (Maria-Doru, Ana-Cosmin}, {ana-Cosmin, Maria-Doru), (Maria-Doru, Doina-Cosmin}, (Doina-Dory, ‘Commin}, (Ana-Doru, Doina-Cosmin}, (Doina-Doru, Ana-Cosmin). 2 Capitolul 4. Metoda backtracking 8. Cel n actionari ai unei firme trebuie s# organizeze un numar maxim de gedinte tip mas rotunda la care s8 participe exact p dintre ei. Stiind c& oricare doua sedinte trebuie sa difere fie prin acfionari prezenti, fie prin vecinii pe care Tl au acestia la masa, stabil numarul de sedinte pe care le pot organiza. De exemplu, dacd nea gi p=3, atunci sunt posibile 5 contiguratiidiferte ale celor 3 actioneri agezati la masa rotund’: 1-2-3; 1-3-2; 1-3-4; 1-4-3; 2-3-6; 2-4-3 (configurafile 2-3-1 gi 3-1-2 nu se considera, deoarece sunt echivalente, la masa rotunda, cu configurafia 1-2-3) 4.4.6, Generarea tuturor partitiilor multimii {1, 2, ..., n} Definijia 4.1. Fie mutimea a(1,2,....n}. Se numeste partitie a § DS "mult a, un sel de Sesu multimi care indeplinesc conditile de mai jos: a) AUALU. «JURA; b) AWNAY=D, Visje(1,2...0), Exemplu. Considerém muljimea a=(1,2,3). Avem partie: {1,2,3) (2,2) (3) (2,3) (@y 12,3) @) (M (@) Gr © Enung. Se cteste un numar naturel, m. Se cer toate partite muitimit Re) 2yveeend. © Rezolvare. Chiar daca stim s& generam toate submultimile unei multimi, tot nu ne ajutd sa generdim toate partite. 2. Pentru a putea genera toate partifile, tebuie sa gasim o metoda prin care sé Putem refine o parte. © prima idee ne conduce la folosirea unui vector, aol, asttel: daca sol [2}=k, alunci elementul & se gseste in mullimea i a partici. Totusi, nu ‘tim cAte muttimi sunt in partiia respectiva. Exist o partie care contine a mulimi alunci cand flecare element este intr-o multime si una care confine toate muiimie, adic tocmai mutimea a. Cu alte cuvinte, numérul multimilor dint'-o partie este intre 4 gin. 2. Pentru a avea o ordine in generarea solutilor, elementele multimii a trebuie sa apar{ina de submultimi consecutive ale partitii, > Din acest motiv, 801 £4) va lua valorifntre 4. $1 demax(sol [1], sol[2], ..., solfi-2]}. 1 Manual de informaticd pentru clasa a XI-a B it sare, de exemplu, vectorul sol retine ee ay submuitimea 4 2 partitiel, ar elementul 2 se gaseste in submulimea 3 a parte. In ‘acest caz, lioseste submultimea 2 a partitie. Sa exemplificam functionarea elgoritmului pentru cazul n=3; = sol=(1,1,1) - Ai={1,2,3)) = sol=(1,2,3) - A={1} Ag={2) As=(3). J 88 observim cnc! in cazulacestei probleme nu trebule sa verficdm existenta @ anumitor condifi' de continuare, ‘Analizati programul astfel obfinut! Varianta Pascal carina Cte: ver solvarrayl0..10}of integer; | @include ‘ineegers | ine n. aod (301, pei max(10],4,j,maxim; procedure tipars ces Cnaacinety for (draitceniiee) Te (nandmcsod (2) fnnimeaol (17 coutccrartivie " maxeprec:=e01 [337 y Manual de informatica pentru clasa a Xl-a us 4 Capitolul 4, Metoda backtracking for isei to maxprecti do begin ‘pol tk] sai back 1) pack (2) ¢ ends > end end; begin weite(tn='); readin(a)s pack(1) end. LP” exorcitiu, Puteti ardia c& orisrel parti fi eparine un unic confinut al vectoruiui so2, obtinut ca in program? Indicatie. Observati o& intotdeauna olementul 4. apartine primei submultini @ paritioi, elementul 2 poate apartine submultimior 1 sau 2 ale partie, lementul n poate epartine suomukimiior, 2, 2 sau n ale partiel, Pomind de aici construit vectorul aoa! : J], Tnand cont de faptul ca orcare parti corespunde un unic continut al J Vectorului #02 si oricdrui confinut al vectorului got ti corespunde © unica partie, am obfinut, practic, 0 functie bijectiv de ta multimea partiilor Muitimii a la multimea continuturilor generate de algoritm ale vectorulul #0. Pornind de la aceasta bijectie, in loc ca algoritmul s& genereze partitile, e! va determina continuturile vectorulul eet. Apoi, pentru fiecare continut al vectorului sot, se obfine o partie. 4 Exercltiu. Modificali programul precedent pentru ca acesta sa afigeze toate partie care contin exact 3 submultin. 4.5. Alte tipuri de probleme care se rezolvd prin utilizarea metodei backtracking 4.5.1, Generalitati Toate problemele pe care le-am intalnit pana acum i admit soluti 0 indeplinesc urmatoarele caracteristc: ne > solutfile sunt sub forma de vector, % {oate solutile nei probleme au aceeasi lungime, unde prin lungime infelegem numacul de componente ale vectorulul solute. Exemple. Fie multimea A=(1,2...m). Atunci: a) Toate permutérile muitimii a au lungimean. 1») Toate submultimile cu p elemente ale mutimil a (generaree combinéfilor) au lungimea p. ce} Toate solutile sub forma de vector ale problemei gener tturor parttitor rmuitimil a au lungimea n. In ealitate, cu ejutorul metode backtracking se pot rezolva gi probleme care Indeplinese condifile de mai sus. Astfl, exista probleme in care Ny Se ccunoaste de la race angimea solu, exist probleme care admit mal multe eolul! 3 lungimi eee nes probleme in care solua este sub forma unel matice cu dous sau Wel lini ete, Exemplele urmatoare va vor convinge. 4,5.2. Generarea partitiilor unui numéar natural 7 Enunt, Se citeste un numar natural a, Se core 88 Se tipareasc’ toate modurile de deevomnpunere a jul ca suma de numere naturale, De exempl, pentty naa, avem: 4, 32, 22, 214, 13, 124, 122, 1414. J, Ordinea aumeretor cin ‘sumé este important. Astfel, se tipareste 112 dar $ siaia, 12a. © Rezolvare. De la inceput, observam ca nu se cunoaste lungimea unei soiuti Ea poate fi cuprinss intre 2, in cazul In care numarul in sine constitule © Gescompunere a s@ si n, atunci cand numarul este descompus ca sum 2 = numero egale cu 4. Trecem la stabilirea algoritmulul pe care fl vor folosl. ‘Le Fiecare component a vectorului set trebuie 8 reting 0 valoare mai mare sau egala cu 1 2 Mal Intéi s& observm c&, in procesul de generare a solutilor, tn permanent s& fie respectata relatia trebuie ca sol [1] +01 [2] +. . .soL(s] Ant sol[100}, m,i,87 procedure back (ktinteger) ; void back(int ) begin (4£ (nen) Lf sen then begin ( for (Gelzicek-a;ie+) for iret torket é eoutece0d 7 write(est(l)y | coutecondiy weltelny lo ena | else lee begin | “CSernas0s nou tk) #20 GEM (oot ta socn) White sol (ki sen do Cacti, ein ereol ty begin weite(*n="); readin(n); back (1) ond. Manual de Informatica pentru clasa a Xl-a uz FA exert 1. Cum trebuie procedat in cazul in care se cere ca solutile 68 fie afigate 0 singura data? Spre exemplu, dac& s-a afigat descompunerea 1, 2,2 sé nu se mai afigeze 2,1,18au1,2,1? Indicafie: procedeul a mai fost intalni, de exemplu f@ generarea combinéslor. Soluile se vor genera in ordine crescétoare, Modifcali programul in acest sens. 2. Adaptati metoda de rezolvare astfel incét s& se genereze numai partitile formate din numere naturale distincte. 3, Adaptali metoda de rezolvare astfel incét s8 se genereze numai partitile formate din cel putin p numere naturale distincte (n gi » citite de la tastetura). 4, Adaptati metoda de rezoivare astfel incat s8 se genereze numai partitile formate din numere naturale aflate in intervalul [a,b] (a, a gi citite de la tastatura) 5. Rezolvati problema scrierli numérului natural n ca suma de numere naturale alese dintr-o multime formata din & valori date {vi, v2, ..., vk}. Astfel, 10 se poate scrie ca sum de numere alese din mukimea {2,3,6} in felul urmator: 10u2+2+24242, 1002424343, 10m24246. 4.5.3. Plata unei sume cu bancnote de valori date 1 Enung. Se dau suma » gin tipuri de monede avand valori de az,a25...a5 lei. Se cer toate modaiitatile de plata a sumel e utlizénd aceste monede. Se presupune & se dispune de un numar nelimitat de exemplare din fiecare tip de moneda latd solutile pentru Suma=5, n=3 (treitipuri de monede) cu valorile 1, 2, 3 1) 1 de 2, 1 de 3; 2) 1 de a, 2 de 2; 3) 2 de 1, 1 de 3; 4) 3 do 1, 1 de 2; 5) 5 do 1; © Rezolvare. Valorile celor n monede sunt refinute de vectorui a. Astfel, a1] va fefine valoarea monedei de tipul 1, a[2] valoarea monedei de tipul 2, g.a.md. Numérul de monede din flecare tip va fl retinut de vectorul sol. Astfel, sol (2) va refine numarul de monede de tipul 1, soi [2] va retine sumarul de monede de tpul 2, g.amd. In aceste conati, o *et [2] 0] 4 solutie pentru exemplul anterior arat ca alaturat, unde suma 5 a 2t3 se formieaza cu dou’ monede de 1 gi o moneda de 3. J cecbservam? ug 1. Exist componente ale vectorulul so. Capitolul 4. Metoda backtracking care refin 0, Aceast® situatie corespunde cazului in care moneda respectivé nu este luaté in calcul. Din acest motiy, fiecare component a vectorului so va finifializata cu o valoare aflata inai posibila, adica cu ~1. tea tuturor celor 2. Orice solutie are exact n componente (n este numarul de tipuri de monede). Acest numa include toate monedele, chiar i cele care nu sunt luate in calcul. 3. Ca gi la problema anterioara, vom retine in permanent suma obtinut’ la un ‘moment dat. Astfel, la pasul i, avem la dispozitie suma 8 = aft] *sol[1] + a[2]*e0l[2] + 4. Avem solutie daca + + alk-2] *sol[k-2) 8 = a[l]*sol(1} + a[2}*s0l(2] + ... + aln]*sol{n] = Suma F” crarot cert 88 arth, prin dasene, ca a problema anteioers, rou de obtinere a tuturor solutiior pentru Suma: sines ‘In continuare, este prezentat programut Varianta Pascal Varianta C++ var sol,atarray{1..100] of integer; n,i,8, Suma: integer; procedure back (ktintagar); begin’ Af exsuna then begin writeln('solutie'); for iis1 to k-1 ao | if gol(4}<>0 then writein (sol[il,' moneds eo *,atil): weiveiny | os | a | begin gol [k] 15-1; | Weide. (aol fe tatahvacsana) | ana (honed) do begin BOL Ik) esol fk +hy siseesol[k)*alkl) | back (keh) 7 sr=e-sol [kl *aCk] end; ona ond #include Ant sol[100], a[100}, 81,8, Soma; void back (int %) C4 (eeesuma) {C cout elae ( soLtkl=-17 while (sol [kI*afk} +s>alid werite(!ns'); readin(n); > for i:sl ton do back(1): ‘begin, > write Catt,4, readin(alil); ena back(1) end. 2 Exercifiu. Adaptati rezolvarea problemei pli unei sumei cu bancnote date. cunoseénd, in plus, pentru fiecare veloare a, numarul limits b, de bancnote cu veloarea respectiva disponibile, Astfel, pentru 8=100, a=(2,5,50), b=(10,6,3), varinata e=1035+1%50 nu corespunde cerinfei deoarece nu avem la dispozitie 10 monede de 5, ci doar 6. 4.5.4, Problema labirintului 7 Enunt. Se dé un labirint sub forma de matrice cu m lini gin coloane, Flecare element al matricei reprezinté o camera a labirintului. Intr-una din camere, de coordonate 1in gi col, se gaseste un om. Se cere s& se gseasca toate iesirile din labirint. Nu este permis ca un drum sa treaca de doua ori prin aceeasi camer’. © prima problema care se pune este precizarea modulul de codificare a iesinitor din fiecare camera a labirintului Fie 1(4, 4) un element al matricei. Acesta poate lua valori intre 0 si 15. Se considera iesirle spre nord, est, sud gi vest, Iuate in aceast& ordine. Pentru fiecare directie cu iesire se retine 2, iar in caz contrar, se refine 0. Un sir de patru cifre 1 sau 0 formeaza un numar in baza 2. Acest numér este convertit In baza 10 gi retinut In 1(4,3). De exemplu, pentru o camera care are iesire in nord si vest, avern 1002,2; Exemplu. Alaturat este prezentat un labirint. Acolo unde nu este permisé trecerea dintr-o camera In alta, 8 marcheaza cu 0 linie oblicé. De asemenea, matrices retine gi valorile corespunzatoare iegirlor, aga curn sunt ele cerute de program. © Rezolvare 1. O camerd vizitaté se retine prin coordonatele ei: 14 (linia) $i co1(colana). Din acest motiv, pentru a refine un traseu vom utiliza 0 matrice cu dow’ coloane si mai multe lini: 601. De exemplu, daca camera initiala este cea de coordonate (2,2) osolitie este (2,2), (2,3), (4,3). CC 120 ____Capitolul 4. Metoda backtracking ‘Manual de informatic& pentru clasa a Xb 121 2. Nu toate solutile au aceeasi lungime, Intrucét exist® trasee de jungime diferit. [vote back(int ky int 13m, Se obtine o solutie atunci cand coordonatele camerei unde s-a intrat sunt in afara procedure matricei (nu au linia intre 2 si m si nu au coloana intre 4. sin). Evident, atunel cand back (k, Lin, col integer) + dn oe eet a gasit o situatie, aceasta se afigeaza CAF aneee |] Linemwes HH | 3. Spunem c& o camera este accesibilé daca existé intrare din camera curenta eipar (Lin, col) 7 caitre ea. Atentie la modul (vedet! programul) In care testém daca o camera este (cit) or {got=nrt) else accesibilé sau nu. Este o operatie In care se testeaza confinutul unui anumit bit. ee ere t a Acesta se obtine efectuand un SI logic intre doua valori. De exemplu, dac’ testim far sot id [01 sans iesirea spre sud, atunci efectuam $I logic intre 0010 ,2;=2:s0) i valoarea refinuta eo tk, 12 relia: ee ae In matrice pentru camera curenta. Daca valoarea ob{inuta este diferité de 0, atunci pol (k,2] tweot? end avem iegire din camera curenta catre sud. 1 for it=i to 4 do 7 cane i of If (LELin, cold and 8<>0) and not case 1: Af (LEinl [col] & 8 ee 1 vizitat(k, 2in-2,col)) 4, Inainte de a intra intr-o camer& accesibild se testeazd daca respectiva camera a mai fost vizitaté sau nu. Pentru aceasta utllizém funciia vizdtae. In caz c& a fost vizitata, se face pasul inapoi Anaiizati programut Varianta G++ Vavlanta Pascal ana 420)" end mot T etadtat Oe; tineeotet)) var soliarray [1..100,1..2] of #include then back (ke, 1in,col+l) 7 integer; Ant sol 100} [2},1{10] (101, back(k+1,1in,col+1); PERE Learray [0,.20,0,.20] of in, col} atop case 3: integer; te i (Lin) (col) & 2 a5 ° nt vinitat (int kine lin, ‘and 2<>0) and not searirdelincotinzegenr | Ini vinitlG wistat de Lined cot) 1 visieat (k, Tinet, col) function visitat (t;Lin, ren pack (ket, lined, col)? ol:integer) :boolean; back(kel,lint1,col); Eset eee 4:4£ (1f1in,col} caso 4: ‘wizivae: ol [i] [2]=-eol) v=ty fend 1<>0) and not i€ (fini [eo] & 1 ae for it=1 to k-1 do return vy wizitat (k,1in,col-1) i vindtat(k, 1in,col-1)) fe (el thea > aaa back (k+1, 1in,eol-1) (sol [i, 2] say (int 7 back(k+1,1in,col-1) eee then vizitatreeruey vold tipar(int Keint Lin, ona; {ease} ,? end; (cout <<" golutie "<cels writeln('iesixe prin est'); < of integer Ant sol (100) £31, e110) (20), trarray [0..10,0..10] n,n, i,4,1in, cols of integer; eatbabe anettc | myn, i,3,1in,colsinteger; | old tipar(int | ° ‘e9e%7 | coutce"solutie * writeln(so1[i,2)," *, sol td, 31)5 void back(int k, int lin, int col) (4f (lineso [| Linsemet’ || eoize0 || colssn+3) back (k,1in, col :integer) ; tapar(k) bogin else 4€ (Lined) or (Linemet) or | { aol) [01=07 (cole0) or (coi=ne1) sol} (1]=14 thon tipar(k) 02 [£2 else begin while (sol [kI 101<4) sol tis fol be, 2} s=tins 01 (kt £0) 03 S01 fk, 3] s=coly switch (201 fk) £01) waiie poltkti<4 do | z begin case 4: 901 fk, 1] #2501 tk, 1) 47 L£(eChin-41 (0011 begin main() write('Ms"); xeadin(m); | C coute>m write('N='); readin in); cout>ay BSE eee EEE eee Eee eee 4 a Capitolul 4, Metoda backtracking -—_ anual de informatick pentru clasa a xi-a 12s : Bee - ; 7 for tvet to m ao for (istyicemsive begin ie Gemnen tor Jiet ton @ for (easiensien) Sf ientn thon (tor Getiteek-asise) | Dain U sue cere rrectveriacehecrieey opin coutcceol (81 f01ee" weiteCet des 'd, eine Gin for ire to kel do <

You might also like