Documente Academic
Documente Profesional
Documente Cultură
satisfăcute, se va alege o altă valoare din mulţimea Sk , până cand fie se va găsi o valoare
pentru care condiţiile de continuare sunt satisfăcute, fie se epuizează toate elementele
mulţimii S k .
În cazul în care se găseşte un element xk convenabil, se trece la pasul k+1. Dacă
1
else k --;
}
Problema 1: să se genereze toate permutările mulţimii A = { 1,2, ..., n}.
# include<iostream.h>
int n, x[100];
int cond (int k)
{
int i;
for(i=1;i<=k-1;i++) if (x[k] = =x[i]) return 0;
return 1;
}
void afisare(int k)
{
for(int i=1;i<=k;i++) cout<<x[i]<<”_” ;
cout<<endl;
}
void BT( )
{
int k;
k=1; x[k]=0;
while (k>0) {
if (x[k] < n) {
x[k]++;
if (cond(k) = =1) if (k= =n) afisare(k);
else { k++; x[k]=0;}
}
else k--;
}
}
void main( )
{
cin>> n;
BT ( );
}
2
Problema 1’: să se genereze recursiv toate permutările mulţimii A = { 1,2, ..., n}.
# include<iostream.h>
int n, x[100];
int cond (int k)
{
int i;
for(i=1;i<=k-1;i++) if (x[k] = =x[i]) return 0;
return 1;
}
void afisare(int k)
{
for(int i=1;i<=k;i++) cout<<x[i]<<”_” ;
cout<<endl;
}
void perm_rec(int k)
{
if(k= =n+1) afisare(k-1);
else for(int j=1;j<=n;j++) {
x[k]=j;
if(cond(k)= =1) perm_rec(k+1);
};
}
void main( )
{
cin>> n;
perm_rec(1);
}
3
Problema 2: Se dă un vector v cu n elemente. Să se genereze toate permutările acestor
elemente.
# include<iostream.h>
int n, x[100], v[100];
void citire( )
{
int i; cin>> n;
for(i=1;i<=n;i++) cin>>v[i];
}
int cond (int k)
{
int i;
for(i=1;i<=k-1;i++) if (x[k] = =x[i]) return 0;
return 1;
}
void afisare(int k)
{
for(int i=1;i<=k;i++) cout<<v[x[i]]<<”_” ;
cout<<endl;
}
void BT( )
{
int k;
k=1; x[k]=0;
while (k>0) {
if (x[k] < n) {
x[k]++;
if (cond(k) = =1) if (k= =n) afisare(k);
else { k++; x[k]=0;}
}
else k--;
}
}
void main( )
{
citire ( );
BT ( );
}
4
Problema 3: să se genereze toate permutările mulţimii A = { 1,2, ..., n} a.î. în orice
permutare, elementele vecine 2 câte 2 să nu fie consecutive.
# include<iostream.h>
int n, x[100];
int cond (int k)
{
int i;
for(i=1;i<=k-1;i++) if (x[k] = =x[i]) return 0;
if(abs(x[k] – x[k-1])<=1 && k>1) return 0;
return 1;
}
void afisare(int k)
{
for(int i=1;i<=k;i++) cout<<x[i]<<”_” ;
cout<<endl;
}
void BT( )
{
int k;
k=1; x[k]=0;
while (k>0) {
if (x[k] < n) {
x[k]++;
if (cond(k) = =1) if (k= =n) afisare(k);
else { k++; x[k]=0;}
}
else k--;
}
}
void main( )
{
cin>> n;
BT ( );
}
5
Problema 4: să se genereze toate aranjamentele de n elemente luate câte p pentru
mulţimea A = { 1,2, ..., n}.
indicaţie: idem permutări, doar că mai citim şi pe p, iar în procedura BT afişarea o facem
dacă k este egal cu p.
# include<iostream.h>
int n, p, x[100];
int cond (int k)
{
int i;
for(i=1;i<=k-1;i++) if (x[k] = =x[i]) return 0;
return 1;
}
void afisare(int k)
{
for(int i=1;i<=k;i++) cout<<x[i]<<”_” ;
cout<<endl;
}
void BT( )
{
int k;
k=1; x[k]=0;
while (k>0) {
if (x[k] < n) {
x[k]++;
if (cond(k) = =1) if (k= =p) afisare(k);
else { k++; x[k]=0;}
}
else k--;
}
}
void main( )
{
cin>> n;
cin>> p;
BT ( );
}
6
Problema 5: se dau n elemente întregi. Să se afle toate aranjările a m elemente din cele n
# include<iostream.h>
int n, m, x[100], v[100];
void citire( )
{
int i; cin>> n;
for(i=1;i<=n;i++) cin>>v[i];
}
int cond (int k)
{
int i;
for(i=1;i<=k-1;i++) if (x[k] = =x[i]) return 0;
return 1;
}
void afisare(int k)
{
for(int i=1;i<=k;i++) cout<<v[x[i]]<<”_” ;
cout<<endl;
}
void BT( )
{
int k;
k=1; x[k]=0;
while (k>0) {
if (x[k] < n) {
x[k]++;
if (cond(k) = =1) if (k= =m) afisare(k);
else { k++; x[k]=0;}
}
else k--;
}
}
void main( )
{
citire( );
cin>> n;
cin>> p;
BT ( );
}
7
Problema 6: să se genereze toate combinările de n elemente luate câte p pentru mulţimea
A = { 1,2, ..., n}.
# include<iostream.h>
int n, p, x[100];
int cond (int k)
{
if( k>1 && x[k]<=x[k-1] ) return 0;
return 1;
}
void afisare(int k)
{
for(int i=1;i<=k;i++) cout<<x[i]<<”_” ;
cout<<endl;
}
void BT( )
{
int k;
k=1; x[k]=0;
while (k>0) {
if (x[k] < n) {
x[k]++;
if (cond(k) = =1) if (k= =p) afisare(k);
else { k++; x[k]=0;}
}
else k--;
}
}
void main( )
{
cin>> n;
cin>> p;
BT ( );
}
8
Problema 7: se dau n persoane prin nume. Să se formeze echipe de câte p persoane.
# include<iostream.h>
# include<stdio.h>
int n, p, x[100];
char v[100][100];
void citire( )
{
int i; cin>> n>>p;
for(i=1;i<=n;i++) gets(v[i]);
}
9
Problema 8: Să se genereze toate submulţimile mulţimii {1, 2, ...., n}.
Se observă că :
- elementele în cadrul unei soluţii sunt în ordine crescătoare şi atunci în cadrul funcţiei
cond (k) trebuie pusă condiţia x[k] > x[k-1]
- deoarece atunci când sunt verificate condiţiile de continuare avem deja o soluţie, aceasta
se afişează direct
# include<iostream.h>
int n, x[100];
int cond (int k)
{
if( k>1 && x[k]<=x[k-1] ) return 0;
return 1;
}
void afisare(int k)
{
for(int i=1;i<=k;i++) cout<<x[i]<<”_” ;
cout<<endl;
}
void BT( )
{
int k;
k=1; x[k]=0;
while (k>0) {
if (x[k] < n) {
x[k]++;
if (cond(k) = =1) {
afisare(k);
k++; x[k]=0;
}
}
else k--;
}
}
void main( )
{
cin>> n;
BT ( );
}
10
Problema 9: Se dau n produse prin numele lor.Să se genereze toate submulţimile de
produse.
# include<iostream.h>
# include<stdio.h>
int n, x[100];
char v[100][100];
int cond (int k)
{
if( k>1 && x[k]<=x[k-1] ) return 0;
return 1;
}
void afisare(int k)
{
for(int i=1;i<=k;i++) cout<<v[x[i]]<<”_” ;
cout<<endl;
}
void BT( )
{
int k;
k=1; x[k]=0;
while (k>0) {
if (x[k] < n) {
x[k]++;
if (cond(k) = =1) {
afisare(k);
k++; x[k]=0;
}
}
else k--;
}
}
void main( )
{
cin>> n;
int i;
for(i=1;i<=n;i++) gets(v[i]);
BT ( );
}
11
Problema 10:se dă un număr natural n. Să se afişeze toate numerele formate din cifre
distincte din n.
Exemplu: n=2324 cifre distincte 3: {2,3,4} 2, 3, 4, 23, 32, 24, 42, 34, 43, 234, ...
Indicatie:
- se formează un vector v (cu m poziţii) din cifrele numărului n.
- soluţiile x[1], ... iau valori de la 1 la m (poziţiile din vectorul v).
- pentru i=1,m aplic BT(i) prin care generez v[x[1]],..., v[x[i]]
# include<iostream.h>
int n, x[100], v[100];
void citire( )
{
int i,c; cin>> n; m=0;
while(n!=0){
c=n%10; n=n/10; b=0;
for(i=1;i<=m;i++) if(c = = v[i]) b=1; generam vectorul v
if (b = = 0) { m++; v[m] = c}
}
}
int cond (int k)
{
for(int i=1;i<=k-1;i++) if (x[k] = =x[i]) return 0;
return 1;
}
void afisare(int k)
{
for(int i=1;i<=k;i++) cout<<v[x[i]]<<”_” ;
cout<<endl;
}
void BT(int p )
{
int k;
k=1; x[k]=0;
while (k>0) {
if (x[k] < m) {
x[k]++;
if (cond(k) = =1) if (k= =p) afisare(k);
else { k++; x[k]=0;}
}
else k--;
}
}
void main( )
{
citire ( );
for (int i=1;i<=m;i++) BT (i);
}
12
Problema 11 (problema celor n dame): pe o tablă de şah de dimensiune n x n trebuie
aşezate n dame a î. ele să nu se ia (să nu se întâlnească pe linie, coloană sau diagonală).
Algoritmul:
- pe fiecare linie se va poziţiona câte o damă , rezultă că soluţia se poate reprezenta sub
forma unui vector x[1], ..., x[n], unde x[i] = coloana damei i, deci x[i] {1, 2, ..., n}.
- condiţiile de continuare sunt reprezentate de faptul că damele nu trebuie să se ia una pe
alta : - pe coloană : pt. i ≠ j x[i] ≠ x[j]
- pe diagonală: | i-j | ≠ | x[i] – x[j] |
# include<iostream.h>
# include <math.h>
int n, x[100];
char a[100][100];
int cond (int k)
{
int i;
for(i=1;i<=k-1;i++) if (x[k] = =x[i]) return 0; // nu se ataca pe col.
for(i=1;i<=k-1;i++) if ( abs(k-i) = = abs( x[k] – x[i] )) return 0; // nu se ataca pe diag.
return 1;
}
void afisare(int k)
{
for(int i=1;i<=k;i++)
for(int j=1;j<=k;j++) a[i][j] = ’*’;
for(int i=1;i<=k;i++) a[i][x[i]] = ’D’
for(int i=1;i<=k;i++) {
for(int j=1;j<=k;j++) cout<<a[i][j]<<”_” ;
cout<<endl;
}
}
void BT( )
{
int k; k=1; x[k]=0;
while (k>0) {
if (x[k] < n) {
x[k]++;
if (cond(k) = =1) if (k= =n) afisare(k);
else { k++; x[k]=0;}
}
else k--;
}
}
void main( )
{
cin>> n;
BT ( );}
13
Problema 11’ (problema celor n dame-recursiv): pe o tablă de şah de dimensiune n x n
trebuie aşezate n dame a î. ele să nu se ia (să nu se întâlnească pe linie, coloană sau
diagonală).
Algoritmul:
- pe fiecare linie se va poziţiona câte o damă , rezultă că soluţia se poate reprezenta sub
forma unui vector x[1], ..., x[n], unde x[i] = coloana damei i, deci x[i] {1, 2, ..., n}.
- condiţiile de continuare sunt reprezentate de faptul că damele nu trebuie să se ia una pe
alta : - pe coloană : pt. i ≠ j x[i] ≠ x[j]
- pe diagonală: | i-j | ≠ | x[i] – x[j] |
# include<iostream.h>
# include <math.h>
int n, x[100];
char a[100][100];
int cond (int k)
{
int i;
for(i=1;i<=k-1;i++) if (x[k] = =x[i]) return 0; // nu se ataca pe col.
for(i=1;i<=k-1;i++) if ( abs(k-i) = = abs( x[k] – x[i] )) return 0; // nu se ataca pe diag.
return 1;
}
void afisare(int k)
{
for(int i=1;i<=k;i++)
for(int j=1;j<=k;j++) a[i][j] = ’*’;
for(int i=1;i<=k;i++) a[i][x[i]] = ’D’
for(int i=1;i<=k;i++) {
for(int j=1;j<=k;j++) cout<<a[i][j]<<”_” ;
cout<<endl;
}
}
void dame_rec(int k)
{
if(k= =n+1) afisare(k-1);
else for(int j=1;j<=n;j++) {
x[k]=j;
if(cond(k)= =1) dame_rec(k+1);
};
}
void main( )
{
cin>> n;
dame_rec(1);
}
14
Problema 12 (problema colorării hărţilor): fiind dată o hartă cu n ţări, se cere o soluţie
de colorare a hărţii utilizând maxim 4 culori a.î. două ţări cu frontieră comună să fie
colorate diferit.
Algoritmul:
- definim o matrice (matricea de adiacenţă): a[i][j] = 1, dacă ţara i e vecină cu ţara j
0, altfel
- cu k notăm ţara, iar x[k] reprezintă culoarea asociată.
- condiţiile de continuare sunt reprezentate de faptul că două ţări cu frontieră comună
trebuie să fie colorate diferit: dacă a[i][j]=1 x[i] ≠ x[j]
# include<iostream.h>
int n, x[100], a[100][100];
void citire ( )
{
cin>>n;
for(int i=1;i<=n;i++)
for(int j=1;j<=n;j++) cin>>a[i][j];
}
int cond (int k)
{
int i;
for(i=1;i<=k-1;i++) if (a[k][i] = =1 && x[k] = = x[i]) return 0;
return 1;
}
void afisare( )
{
int i;
for(i=1;i<=n;i++) cout<<”ţara”<<i<<”are culoarea”<<x[i]<<endl ;
cout<<endl;
}
void BT( )
{
int k;
k=1; x[k]=0;
while (k>0) {
if (x[k] < 4) {
x[k]++;
if (cond(k) = =1) if (k= =n) afisare( );
else { k++; x[k]=0;}
}
else k--;
}
}
void main( )
{
citire ( );
BT ( );}
15
Problema 13 (generarea partiţiilor unui număr natural n): se citeşte un nr. natural n.
Să se tipărească toate modurile de escompunere a lui ca sumă de numere naturale.
Se observă că : 1« x[1] « n
1« x[2] « n-1
...........................
1« x[k] « n-k+1
# include<iostream.h>
int n, x[100];
int cond (int k)
{
int i, S=0;
for(i=1;i<=k;i++) S=S+x[i];
if (S= =n) return 1;
else return 0;
}
void afisare(int k)
{
for(int i=1;i<=k;i++) cout<<x[i]<<”_” ;
cout<<endl;
}
void BT( )
{
int k;
k=1; x[k]=0;
while (k>0) {
if (x[k] < n-k+1) {
x[k]++;
if (cond(k) = =1) afisare(k);
else { k++; x[k]=0;}
}
else k--;
}
}
void main( )
{
cin>> n;
BT ( );
}
16
Problema 14 ( produsul cartezian a n mulţimi): se dau mulţimile A1, A2, ..., An, unde
Ai = {1, 2, ..., vi}, i=1,n. Se cere produsul cartezian al celor n mulţimi.
Algoritmul:
- se citesc n, un vector v[n], unde v[i] = nr. de elemente din Ai.
- orice element x[k] este valid
- limita superioră a lui x[k] nu mai este n, ci v[k]
# include<iostream.h>
int n, x[100], v[100];
void afisare(int k)
{
for(int i=1;i<=k;i++) cout<<x[i]<<”_” ;
cout<<endl;
}
void BT( )
{
int k;
k=1; x[k]=0;
while (k>0) {
if (x[k] < v[k]) {
x[k]++;
if (k= =n) afisare(k);
else { k++; x[k]=0;}
}
else k--;
}
}
void main( )
{
int i;
cin>> n;
for(i=1;i<=n;i++) cin>>v[i];
BT ( );
}
17
Problema 15: se dă un număr natural n par. Să se determine toate şirurile de n paranteze
care se închid corect.
Exemplu : pentru n = 6: ((( ))) () (( )) (( )) () () () () (( )( ))
Trebuie să găsim submulţimi ale lui A a. î. intersectate 2 câte 2 dau mulţimea vidă şi
reunite toate, dau mulţimea A.
18