This shows you the differences between two versions of the page.
|
pa:laboratoare:laborator-04 [2026/03/21 17:18] radu.nichita |
pa:laboratoare:laborator-04 [2026/03/27 02:05] (current) radu.nichita |
||
|---|---|---|---|
| Line 8: | Line 8: | ||
| ===== Precizări inițiale ===== | ===== Precizări inițiale ===== | ||
| <note> | <note> | ||
| - | Toate exemplele de cod se găsesc pe pagina [[https://github.com/acs-pa/pa-lab/tree/main/demo/lab05|pa-lab::demo/lab05]]. | + | Toate exemplele de cod se găsesc pe pagina [[https://github.com/acs-pa/pa-lab/tree/main/algorithms/lab04|pa-lab::algorithms/lab04]]. |
| Exemplele de cod apar încorporate și în textul laboratorului pentru a facilita parcurgerea cursivă a acestuia. ATENȚIE! Varianta actualizată a acestor exemple se găsește întotdeauna pe GitHub. | Exemplele de cod apar încorporate și în textul laboratorului pentru a facilita parcurgerea cursivă a acestuia. ATENȚIE! Varianta actualizată a acestor exemple se găsește întotdeauna pe GitHub. | ||
| Line 72: | Line 72: | ||
| ===== Exemple clasice ===== | ===== Exemple clasice ===== | ||
| Ne vom ocupa în continuare de următoarele probleme: | Ne vom ocupa în continuare de următoarele probleme: | ||
| - | * Permutări | + | * Permutări |
| - | * Combinări | + | * Combinări |
| - | * Aranjamente | + | * Aranjamente |
| - | * Submulțimi | + | * Submulțimi |
| - | * Generare de șiruri | + | * Generare de șiruri |
| - | * Problema damelor | + | * Problema damelor |
| - | * Problema șoricelului | + | * Problema șoricelului |
| - | * Tic-Tac-Toe | + | * Tic-Tac-Toe |
| - | * Sudoku | + | * Sudoku |
| - | * Ultimate Tic-Tac-Toe | + | * Ultimate Tic-Tac-Toe |
| <note> | <note> | ||
| Line 179: | Line 179: | ||
| Soluția va avea următoarele complexitati: | Soluția va avea următoarele complexitati: | ||
| - | * complexitate temporala : $T(n)=O(n * n!)$ | + | * complexitate temporala : $T(n)=O(n * n!)$ |
| - | * explicație : Complexitatea generarii permutarilor, $O(n!)$, se înmultește cu complexitatea copierii vectorilor soluție si domeniu si a stergerii elementelor din domeniu, $O(n)$ | + | * explicație : Complexitatea generarii permutarilor, $O(n!)$, se înmultește cu complexitatea copierii vectorilor soluție si domeniu si a stergerii elementelor din domeniu, $O(n)$ |
| - | * complexitate spatiala : $S(n)=O(n^2)$ | + | * complexitate spatiala : $S(n)=O(n^2)$ |
| - | * explicație : Fiecare nivel de recursivitate are propria lui copie a soluției și a domeniului. Sunt n nivele de recursivitate, deci complexitatea spatială este $O(n * n) = O(n^2)$ | + | * explicație : Fiecare nivel de recursivitate are propria lui copie a soluției și a domeniului. Sunt n nivele de recursivitate, deci complexitatea spatială este $O(n * n) = O(n^2)$ |
| Line 735: | Line 735: | ||
| * explicație: stocam maximum $2n-1$ căsuțe | * explicație: stocam maximum $2n-1$ căsuțe | ||
| - | ===== Exerciții ===== | + | ===== Pool probleme (pentru prezentări) ====== |
| - | <note> | + | |
| - | Scheletul de laborator se găsește pe pagina [[https://github.com/acs-pa/pa-lab/tree/main/skel/lab05|pa-lab::skel/lab05]]. | + | ======= 1) Word Search ======= |
| - | </note> | + | |
| - | ==== Aranjamente ==== | + | **Enunt:** Se dă o matrice de dimensiuni ''m × n'' formată din litere și un cuvânt ''word''. Determinați dacă acest cuvânt poate fi format în matrice. |
| - | Fie N și K două **numere naturale strict pozitive**. Se cere afișarea tuturor aranjamentelor de N elemente luate cate K din mulțimea {1, 2, ..., N}. | + | Cuvântul se construiește unind litere din celule adiacente (pe orizontală sau verticală). Nu aveți voie să folosiți aceeași celulă de două ori în formarea aceluiași cuvânt. |
| + | |||
| + | **Date de intrare:** O matrice de caractere de dimensiuni ''m × n'' și un șir de caractere ''word''. | ||
| + | |||
| + | **Date de ieșire:** Se afișează ''true'' dacă cuvântul există în matrice, altfel ''false''. | ||
| + | |||
| + | Problema se poate testa la: | ||
| + | https://leetcode.com/problems/word-search/ | ||
| + | |||
| + | ======= 2) Combination Sum II ======= | ||
| + | |||
| + | **Enunt:** Se dă un șir de numere (care poate conține duplicate) și un număr țintă ''target''. Găsiți toate combinațiile unice de elemente din șir a căror sumă este exact ''target''. | ||
| + | Fiecare element de pe o anumită poziție din șir poate fi folosit cel mult o dată într-o combinație. Setul final de soluții nu trebuie să conțină combinații duplicate. | ||
| + | |||
| + | **Date de intrare:** Un vector de numere întregi ''candidates'' și un număr întreg ''target''. | ||
| + | |||
| + | **Date de ieșire:** O listă de liste de numere întregi, reprezentând combinațiile unice valide. | ||
| + | |||
| + | Problema se poate testa la: | ||
| + | https://leetcode.com/problems/combination-sum-ii/ | ||
| + | |||
| + | ======= 3) Gray Code ======= | ||
| + | |||
| + | **Enunt:** Codul Gray de ordin ''n'' este o secvență ce conține toate cele $2^n$ șiruri binare de lungime ''n'', cu proprietatea că oricare două șiruri consecutive diferă prin exact un singur bit. | ||
| + | Cerința este să generați o astfel de secvență validă pentru un ''n'' dat. | ||
| + | |||
| + | **Date de intrare:** Un număr întreg ''n'' — lungimea șirurilor de biți. | ||
| + | |||
| + | **Date de ieșire:** Se afișează secvența de $2^n$ numere (în format zecimal sau binar), respectând regula codului Gray. | ||
| + | |||
| + | Problema se poate testa la: | ||
| + | https://cses.fi/problemset/task/2205 | ||
| + | |||
| + | ======= 4) Sudoku Solver ======= | ||
| + | |||
| + | **Enunt:** Vi se cere să scrieți un program care rezolvă un puzzle Sudoku clasic (9 × 9) prin completarea celulelor goale. | ||
| + | Pentru ca soluția să fie validă, trebuie respectate regulile clasice: fiecare cifră de la 1 la 9 trebuie să apară o singură dată pe fiecare rând, pe fiecare coloană și în fiecare dintre cele nouă careuri 3 × 3. | ||
| + | |||
| + | **Date de intrare:** O matrice 9 × 9 de caractere reprezentând tabla de Sudoku inițială (celulele goale sunt marcate cu caracterul ''.''). | ||
| + | |||
| + | **Date de ieșire:** Matricea 9 × 9 completată cu soluția corectă. | ||
| + | |||
| + | Problema se poate testa la: | ||
| + | https://leetcode.com/problems/sudoku-solver/ | ||
| + | |||
| + | ======= 5) Palindrome Partitioning ======= | ||
| + | |||
| + | **Enunt:** Se dă un șir de caractere ''s''. Se cere să împărțiți șirul în fragmente, astfel încât fiecare fragment (subșir) rezultat să fie un palindrom. | ||
| + | Returnați toate aceste partiționări posibile. | ||
| - | <spoiler Exemplu 1> | + | **Date de intrare:** Un șir de caractere ''s''. |
| + | |||
| + | **Date de ieșire:** O listă de liste de șiruri de caractere, unde fiecare listă interioară reprezintă o partiționare validă. | ||
| + | |||
| + | Problema se poate testa la: | ||
| + | https://leetcode.com/problems/palindrome-partitioning/ | ||
| + | |||
| + | ======= 6) Knight's Tour ======= | ||
| + | |||
| + | Enunt: Se cere să găsiți o parcurgere validă a unei table de șah de dimensiuni 8 × 8 folosind un cal, astfel încât acesta să viziteze fiecare celulă a tablei exact o singură dată. Mutările trebuie să respecte regulile clasice de șah pentru cal (în formă de "L"). | ||
| + | |||
| + | Date de intrare: Două numere întregi ''x'' și ''y'', care indică poziția inițială a calului pe tablă (coloana și rândul). | ||
| + | |||
| + | Date de ieșire: O matrice 8 × 8 în care fiecare celulă conține numărul pasului (de la 1 la 64) la care a fost vizitată respectiva poziție. | ||
| + | |||
| + | Problema se poate testa la: | ||
| + | |||
| + | https://cses.fi/problemset/task/1689 | ||
| + | |||
| + | ===== Extra ===== | ||
| + | |||
| + | ==== Exerciții ==== | ||
| + | <spoiler Aranjamente> | ||
| + | Fie N și K două **numere naturale strict pozitive**. Se cere afișarea tuturor aranjamentelor de N elemente luate cate K din mulțimea {1, 2, ..., N}. | ||
| + | **Exemplu 1:** | ||
| Fie N = 3, K = 2 => M = {1, 2, 3} | Fie N = 3, K = 2 => M = {1, 2, 3} | ||
| Line 753: | Line 825: | ||
| * {3, 1} | * {3, 1} | ||
| * {3, 2} | * {3, 2} | ||
| - | |||
| - | </spoiler> | ||
| <note> | <note> | ||
| Line 760: | Line 830: | ||
| </note> | </note> | ||
| - | <spoiler Hint> | + | **Hint:** Folosiți-vă de problema **Permutări**. |
| - | Folosiți-vă de problema **Permutări**. | + | |
| - | </spoiler> | + | |
| <note> | <note> | ||
| Line 770: | Line 837: | ||
| Checkerul așteaptă să le stocați în această ordine. | Checkerul așteaptă să le stocați în această ordine. | ||
| </note> | </note> | ||
| + | </spoiler> | ||
| - | ==== Submulțimi ==== | + | <spoiler Submulțimi> |
| Fie N un **număr natural strict pozitiv**. Se cere afișarea tuturor submulțimilor mulțimii {1, 2, ..., N}. | Fie N un **număr natural strict pozitiv**. Se cere afișarea tuturor submulțimilor mulțimii {1, 2, ..., N}. | ||
| - | <spoiler Exemplu 1> | + | **Exemplu 1:** |
| Fie N = 4 => M = {1, 2, 3, 4} | Fie N = 4 => M = {1, 2, 3, 4} | ||
| Line 795: | Line 862: | ||
| {3, 4} | {3, 4} | ||
| {4} | {4} | ||
| - | |||
| - | </spoiler> | ||
| - | |||
| <note> | <note> | ||
| Line 803: | Line 867: | ||
| </note> | </note> | ||
| - | <spoiler Hint> | + | **Hint:** Folosiți-vă de problema **Combinari**. |
| - | + | ||
| - | Folosiți-vă de problema **Combinari**. | + | |
| - | + | ||
| - | </spoiler> | + | |
| <note> | <note> | ||
| Line 814: | Line 874: | ||
| Checkerul așteaptă să le stocați în această ordine. | Checkerul așteaptă să le stocați în această ordine. | ||
| </note> | </note> | ||
| + | </spoiler> | ||
| - | ==== Problema damelor ==== | + | <spoiler Problema damelor> |
| Problema damelor (sau problema reginelor) tratează plasarea a 8 regine de sah pe o tablă de șah de dimensiuni 8 x 8 astfel încat să nu existe două regine care se amenință reciproc. Astfel, se caută **o soluție** astfel încât nicio pereche de doua regine să nu fie pe același rând, pe aceeași coloană, sau pe aceeași diagonală. Problema cu opt regine este doar un caz particular pentru problema generală, care presupune plasarea a N regine pe o tablă de șah N x N în aceleasi condiții. Pentru această problemă, există soluții pentru toate numerele naturale N cu excepția lui N = 2 si N = 3. | Problema damelor (sau problema reginelor) tratează plasarea a 8 regine de sah pe o tablă de șah de dimensiuni 8 x 8 astfel încat să nu existe două regine care se amenință reciproc. Astfel, se caută **o soluție** astfel încât nicio pereche de doua regine să nu fie pe același rând, pe aceeași coloană, sau pe aceeași diagonală. Problema cu opt regine este doar un caz particular pentru problema generală, care presupune plasarea a N regine pe o tablă de șah N x N în aceleasi condiții. Pentru această problemă, există soluții pentru toate numerele naturale N cu excepția lui N = 2 si N = 3. | ||
| - | <spoiler Exemplu 1> | + | **Exemplu 1:** |
| Fie N = 5 | Fie N = 5 | ||
| Line 833: | Line 892: | ||
| X reprezintă o damă, - reprezintă spațiu gol. | X reprezintă o damă, - reprezintă spațiu gol. | ||
| - | </spoiler> | + | **Hint:** E nevoie să facem backtracking pe matrice sau e suficient pe vector? |
| - | + | ||
| - | + | ||
| - | <spoiler Hint> | + | |
| - | + | ||
| - | E nevoie să facem backtracking pe matrice sau e suficient pe vector? | + | |
| - | + | ||
| - | </spoiler> | + | |
| - | + | ||
| <note> | <note> | ||
| Se va caută o singură soluție (**oricare** soluție corectă), care va fi returnată sub forma unui vector cu $n + 1$ elemente. | Se va caută o singură soluție (**oricare** soluție corectă), care va fi returnată sub forma unui vector cu $n + 1$ elemente. | ||
| - | |||
| Soluția este $sol[0], sol[1], ..., sol[n]$, unde $sol[i]$ = coloana unde vom plasa regina de pe linia i. | Soluția este $sol[0], sol[1], ..., sol[n]$, unde $sol[i]$ = coloana unde vom plasa regina de pe linia i. | ||
| Elementul 0 este nefolosit, dorim să păstrăm convenția cu indexare de la 1. | Elementul 0 este nefolosit, dorim să păstrăm convenția cu indexare de la 1. | ||
| - | |||
| </note> | </note> | ||
| - | ==== Generare de șiruri ==== | + | </spoiler> |
| + | <spoiler Generare de șiruri> | ||
| Vi se dă o listă de caractere și o lista de frecvențe (pentru caracterul de pe | Vi se dă o listă de caractere și o lista de frecvențe (pentru caracterul de pe | ||
| poziția i, frecvența de pe poziția i). Vi se cere să generați toate șirurile | poziția i, frecvența de pe poziția i). Vi se cere să generați toate șirurile | ||
| Line 860: | Line 909: | ||
| mai mult de K apariții consecutive ale aceluiași caracter. | mai mult de K apariții consecutive ale aceluiași caracter. | ||
| - | <spoiler Exemplu 1> | + | **Exemplu 1:** |
| Fie caractere[] = {'a', 'b', 'c'}, freq[] = {1, 1, 2}, K = 5 | Fie caractere[] = {'a', 'b', 'c'}, freq[] = {1, 1, 2}, K = 5 | ||
| Line 878: | Line 926: | ||
| * ccba | * ccba | ||
| - | </spoiler> | + | **Exemplu 2:** |
| - | + | ||
| - | <spoiler Exemplu 2> | + | |
| Fie caractere[] = {'b', 'c'}, freq[] = {3, 2}, K = 2 | Fie caractere[] = {'b', 'c'}, freq[] = {3, 2}, K = 2 | ||
| Line 892: | Line 937: | ||
| * cbbcb | * cbbcb | ||
| * cbcbb | * cbcbb | ||
| - | |||
| - | </spoiler> | ||
| - | |||
| <note> | <note> | ||
| Line 901: | Line 943: | ||
| Checkerul așteaptă să le stocați în această ordine. | Checkerul așteaptă să le stocați în această ordine. | ||
| </note> | </note> | ||
| - | ===== Bonus ===== | + | </spoiler> |
| - | + | ||
| - | ==== Problema damelor (AC3) ==== | + | |
| + | <spoiler Problema damelor (AC3)> | ||
| **Aplicați AC3 pe problema damelor.** | **Aplicați AC3 pe problema damelor.** | ||
| Line 916: | Line 957: | ||
| O variabilă poate lua orice valoare din domeniul său la orice pas. O constrângere este o relație sau o limitare a unor variabile. | O variabilă poate lua orice valoare din domeniul său la orice pas. O constrângere este o relație sau o limitare a unor variabile. | ||
| - | === Exemplu AC-3 === | + | **Exemplu AC-3:** |
| Considerăm A, o variabilă ce are domeniul D(A) = {0, 1, 2, 3, 4, 5, 6} și B o variabila ce are domeniul D(B) = {0, 1, 2, 3, 4}. Cunoaștem constrângerile: C1 = "A trebuie să fie impar" și C2 = "A + B trebuie să fie egal cu 5". | Considerăm A, o variabilă ce are domeniul D(A) = {0, 1, 2, 3, 4, 5, 6} și B o variabila ce are domeniul D(B) = {0, 1, 2, 3, 4}. Cunoaștem constrângerile: C1 = "A trebuie să fie impar" și C2 = "A + B trebuie să fie egal cu 5". | ||
| Line 923: | Line 964: | ||
| AC-3 a redus astfel domeniile lui A si B, reducând semnificativ timpul folosit de algoritmul backtracking. | AC-3 a redus astfel domeniile lui A si B, reducând semnificativ timpul folosit de algoritmul backtracking. | ||
| + | </spoiler> | ||
| - | <hidden> | + | <spoiler Immortal> |
| - | ===== Pool probleme (pentru prezentări) ====== | + | [[https://www.infoarena.ro/problema/immortal | Enunt]] |
| - | ======= 1) Word Search ======= | + | **Solutie:** |
| - | + | ||
| - | **Enunt:** Se dă o matrice de dimensiuni ''m × n'' formată din litere și un cuvânt ''word''. Determinați dacă acest cuvânt poate fi format în matrice. | + | |
| - | Cuvântul se construiește unind litere din celule adiacente (pe orizontală sau verticală). Nu aveți voie să folosiți aceeași celulă de două ori în formarea aceluiași cuvânt. | + | |
| - | + | ||
| - | **Date de intrare:** O matrice de caractere de dimensiuni ''m × n'' și un șir de caractere ''word''. | + | |
| - | + | ||
| - | **Date de ieșire:** Se afișează ''true'' dacă cuvântul există în matrice, altfel ''false''. | + | |
| - | + | ||
| - | Problema se poate testa la: | + | |
| - | https://leetcode.com/problems/word-search/ | + | |
| - | + | ||
| - | ======= 2) Combination Sum II ======= | + | |
| - | + | ||
| - | **Enunt:** Se dă un șir de numere (care poate conține duplicate) și un număr țintă ''target''. Găsiți toate combinațiile unice de elemente din șir a căror sumă este exact ''target''. | + | |
| - | Fiecare element de pe o anumită poziție din șir poate fi folosit cel mult o dată într-o combinație. Setul final de soluții nu trebuie să conțină combinații duplicate. | + | |
| - | + | ||
| - | **Date de intrare:** Un vector de numere întregi ''candidates'' și un număr întreg ''target''. | + | |
| - | + | ||
| - | **Date de ieșire:** O listă de liste de numere întregi, reprezentând combinațiile unice valide. | + | |
| - | + | ||
| - | Problema se poate testa la: | + | |
| - | https://leetcode.com/problems/combination-sum-ii/ | + | |
| - | + | ||
| - | ======= 3) Gray Code ======= | + | |
| - | + | ||
| - | **Enunt:** Codul Gray de ordin ''n'' este o secvență ce conține toate cele $2^n$ șiruri binare de lungime ''n'', cu proprietatea că oricare două șiruri consecutive diferă prin exact un singur bit. | + | |
| - | Cerința este să generați o astfel de secvență validă pentru un ''n'' dat. | + | |
| - | + | ||
| - | **Date de intrare:** Un număr întreg ''n'' — lungimea șirurilor de biți. | + | |
| - | + | ||
| - | **Date de ieșire:** Se afișează secvența de $2^n$ numere (în format zecimal sau binar), respectând regula codului Gray. | + | |
| - | + | ||
| - | Problema se poate testa la: | + | |
| - | https://cses.fi/problemset/task/2205 | + | |
| - | + | ||
| - | ======= 4) Sudoku Solver ======= | + | |
| - | + | ||
| - | **Enunt:** Vi se cere să scrieți un program care rezolvă un puzzle Sudoku clasic (9 × 9) prin completarea celulelor goale. | + | |
| - | Pentru ca soluția să fie validă, trebuie respectate regulile clasice: fiecare cifră de la 1 la 9 trebuie să apară o singură dată pe fiecare rând, pe fiecare coloană și în fiecare dintre cele nouă careuri 3 × 3. | + | |
| - | + | ||
| - | **Date de intrare:** O matrice 9 × 9 de caractere reprezentând tabla de Sudoku inițială (celulele goale sunt marcate cu caracterul ''.''). | + | |
| - | + | ||
| - | **Date de ieșire:** Matricea 9 × 9 completată cu soluția corectă. | + | |
| - | + | ||
| - | Problema se poate testa la: | + | |
| - | https://leetcode.com/problems/sudoku-solver/ | + | |
| - | + | ||
| - | ======= 5) Palindrome Partitioning ======= | + | |
| - | + | ||
| - | **Enunt:** Se dă un șir de caractere ''s''. Se cere să împărțiți șirul în fragmente, astfel încât fiecare fragment (subșir) rezultat să fie un palindrom. | + | |
| - | Returnați toate aceste partiționări posibile. | + | |
| - | + | ||
| - | **Date de intrare:** Un șir de caractere ''s''. | + | |
| - | + | ||
| - | **Date de ieșire:** O listă de liste de șiruri de caractere, unde fiecare listă interioară reprezintă o partiționare validă. | + | |
| - | + | ||
| - | Problema se poate testa la: | + | |
| - | https://leetcode.com/problems/palindrome-partitioning/ | + | |
| - | </hidden> | + | |
| - | + | ||
| - | ===== Extra ===== | + | |
| - | + | ||
| - | ==== Immortal ==== | + | |
| - | + | ||
| - | [[https://www.infoarena.ro/problema/immortal | Enunt]] | + | |
| - | <spoiler Solutie> | + | |
| [[http://olimpiada.info/oji2010/index.php?cid=arhiva | OJI 2010 - clasele 11-12]] | [[http://olimpiada.info/oji2010/index.php?cid=arhiva | OJI 2010 - clasele 11-12]] | ||
| </spoiler> | </spoiler> | ||
| - | |||
| - | |||
| <spoiler Backtracking problems> | <spoiler Backtracking problems> | ||