Documente Academic
Documente Profesional
Documente Cultură
Exemple:
a = 2, n = 10 → 1024
a = 3, n = 7 → 2187
Dupa ce rezolvati, determinati complexitatea algoritmului
- se citesc a,n
- rez = 1
- cat timp n > 0 executa
- rez = rez*a
- n = n-1
- se afiseaza rez → Complexitate O(n)
- rez = 1
- cat timp (n>0) executa
- daca n%2 == 1 atunci
- rez = rez * a
- a = a*a
- n = n/2
- se afiseaza rez → complexitatea este acea putere a lui 2 care il acopera pe n → O(log(2)n)
Verificarea temei
3. Paranteze: Se citesc n si o secventa de 0-uri si 1-uri, unde 0 reprezinta o paranteza deschisa
‘(’ si 1 reprezinta o paranteza inchisa ‘)’. Sa se spuna daca secventa de paranteze este corecta
si, daca da, sa se spuna si factorul de imbricare (numarul de paranteze interioare). !! Rezolvare
fara vectori !!
Exemple:
n = 8 si secventa 0 1 0 0 1 0 1 1 se va afisa:
DA
2
Obs: Nivelul de imbricare este 2 pt ca, in traducere am avea ()(()())
n = 8 si secventa 0 0 0 1 1 1 0 0 se va afisa:
NU
Idei de rezolvare?
Rezolvare
#include <iostream> Ce complexitate avem in cazul acestei
using namespace std;
solutii?
int main() {
int n, a, i, nrdesc, max;
cin>>n; Complexitatea = O(n)
max = nrdesc = i = 0;
while ( i < n && nrdesc >= 0 ) {
cin>>a;
if ( a == 0 ) {
nrdesc++;
if ( nrdesc > max ) {
max = nrdesc;
}
} else {
nrdesc--;
}
i++;
}
if ( nrdesc == 0 ) {
cout<<"DA"<<endl<<max;
}
else {
cout<<"NU";
}
return 0;
}
Ciurul lui Eratostene - utilizare
1. sa presupunem ca vrem sa determinam toate numerele prime pana la un n dat;
2. se creeaza o lista a intregilor consecutivi de la 2 la n → 2 3 4 … n;
3. se cauta primul numar “netaiat” din lista (initial toate numerele sunt
netaiate);
4. sa presupunem ca primul numar netaiat este p;
5. se merge in lista din p in p incepand cu 2*p si se taie toate numerele
intalnite (unele vor fi deja taiate);
6. se reia pasul 3 pana ce se depaseste n.
v = 0 0 0 0 0 0 0 0
2 3 4 5 6 7 8 9
- primul indice netaiat este 2 → vom taia 4,6,8, deci v devine:
v = 0 0 1 0 1 0 1 0
2 3 4 5 6 7 8 9
- al doilea indice netaiat este 3 → vom taia 6,9 deci v devine:
v = 0 0 1 0 1 0 1 1
2 3 4 5 6 7 8 9
- al treilea indice netaiat este 5 → nu avem ce sa taiem
- al patrulea indice netaiat este 7 → nu avem ce sa taiem
- nu mai exista indici netaiati dupa 7 → numerele prime mai mici sau egale cu 9 sunt 2 3 5 7
Obs: Pentru a optimiza spatiul de memorie folosit, vom folosi vectorul de frecventa ca fiind un vector de
caractere, preluand valorile intregi 0 si 1 ca in exemplu → de ce este “mai optim” asa?
Ciurul lui Eratostene - Solutie I
#include <iostream>
using namespace std;
char v[2000002];
int main()
{
int n,i,d;
cin>>n;
for (i = 2; i < n; i++) { // se parcurg toate valorile din vectorul de frecventa
if (v[i] == 0) { // daca elementul curent este netaiat
for (d = i + i; d <= n; d = d + i) { // se taie toate elementele din i in i, pornind de la 2*i
v[d] = 1;
}
}
}
for (i = 2; i <= n; i++) { // se parcur elementele si se afiseaza cele netaiate
if (v[i] == 0) {
cout<<i<<" ";
}
}
return 0;
}
Logic de rezolvare:
- se construieste ciurul pentru 1300000 numere → vectorul va avea 13000001
- se va afisa al k+1-lea numar prim la puterea a doua (atentie la tipul de date)
In C++
Tema
2. http://varena.ro/problema/extraprime
Logic de rezolvare:
-
In C++
Tema
3. https://infoarena.ro/problema/cmmdc2
Logic de rezolvare:
-
In C++