Curs 3 3.3. Structura repetitiva Alexandru IOVANOVICI
3.3 Structura repetitiva Se foloseste pentru a implementa operatii care se repeta de mai multe ori in cadrul programului; Diferitii pasi difera foarte putin unul de celalalt prin niste marimi usor de pus identificat si reprezentat; Intotdeauna exista un sfarsit (! finitudine)
P.3.3.1 Suma cifrelor unui numar (1) Se citeste un numar intreg  n . Sa se calculeze si sa se afiseze suma cifrelor sale. Ex:   n=1234 => S=1+2+3+4=10 Pseudocod: citeste n cat timp (n<>0) executa { u=n mod 10; S=S+u; } afiseza S
P.3.3.1 Suma cifrelor unui numar (2) Citeste n n<>0 u=n mod 10; S=S+u n=n/10 Scrie S
P.3.3.1 Suma cifrelor unui numar (3) #include <conio.h> #include <iostream.h> int  main  ( void )   { int  n, S = 0 ; cout<<”N =  “; cin>>n; while   ( n  !=   0 )   {   S = S + n % 10 ; n = n / 10 ; } cout<<”Suma cifrelor numarului “<<n<<” este “<<S; return   0 ; }
P 3.3.2. Produsul cifrelor unui numar Tema !!! Similar cu P3.3.1; Atentie la initializarea lui P
P3.3.3 Numere pana la citirea unui nr. (1) Se citeste un numar intreg  n  de la tastatura. Mai apoi se citesc numere intregi pana la introducerea lui  n . Sa se calculeze si sa se afiseze media aritmetica a numerelor introduse (fara  n ); Atentie la tipul de date al mediei;
P3.3.3 Numere pana la citirea unui nr. (2) #include <conio.h> #include <iostream.h> int  main  ( void )   { int  n,ct = 0 ; //in ct numar cate numere am float  M; cout<<”Introduceti numarul cu rol de terminator :  “; cin>>n; int  nc = 0 ; //in nc voi pastra cate un numar citit pe rand while   ( nc != n )   { cout<<”Numarul curent este :  ”; cin>>nc; S = S + nc; ct ++ ; } cout<<”Media celor “<<ct - 1 <<” numere este “<<S /( ct - 1 ) ; return   0 ; }
P3.3.4 Sirul lui Fibbonaci (1) Sa se afiseze primii  n  termeni ai sirului lui Fibbonaci; SB se construieste in felul urmator: Primii doi termeni sunt 1 (Fb[1]=1, Fb[2]=1); Pentru urmatorii termeni este valabila regula: fiecare termen este egal cu suma dintre precedentul si anteprecedentul; (Fb[k] = Fb[k-1] + Fb[k-2]) Exemplu: Fb: 1, 1, 2, 3, 5, 8, 13, 21, 34, 55, ...
P3.3.4 Sirul lui Fibbonaci (2) #include <conio.h> #include <iostream.h> int  main  ( void )   { int  tc;  //termenul curent din sir int  ta = 1 ;  //termenul anterior din sir int  taa = 1 ;  //termenul ante-anterior din sir int  n; cout<<”N =  “; cin>>n; for   ( int  i = 3 ;i< n ;i ++){ tc = ta + taa; cout<<tc<<” “; taa = ta; ta = tc; } return   0 ; }
P3.3.4 Maximul unui sir de numere (1) Se citesc numere  naturale  pana la introducerea lui zero (0); Sa se determine si sa se afiseze maximul dintre numerele citite; Exemplu: Sirul este: 2,1,3,4,2,7,8,0 Maximul este: 8
P3.3.4 Maximul unui sir de numere (2) #include <conio.h> #include <iostream.h> #include <limits.h> int  main  ( void ){ unsigned   int  nc = 1 , max =- UINT_MAX; while   ( nc != 0 ){ cout<< &quot;Introduceti un numar: &quot; ; cin>>nc; if   ( nc>max ){ max = nc; } } cout<< &quot;Maximul este: &quot; <<max<<endl; return   0 ; }
P3.3.5 Minimul unui sir de numere Tema !!! Problema P3.3.4 dar in loc de maxim se va calcula minimul; Consultati continutul fisierului  limits.h
P3.3.6 Verificarea primalitatii (1) Se citeste un numar  natural . Sa se verifice si sa se afiseze daca acest numar este prim sau nu. Un numar este  prim  daca nu are drept divizori decat pe 1 si pe el insusi; Exemplu: Numarul 7: Este prim (nu are alti divizori); Numarul 8: Nu este prim (are divizori pe 2,4)
P3.3.6 Verificarea primalitatii (2) Metodologia: Se citeste numarul; Se presupune ca numarul este prim (prim=1); Se parcurge cu un contor de la  2  la  n/2  si se verifica daca este divizibil cu unul dintre acestea; In caz afirmativ variabila care indica primalitatea devine falsa (prim=0); La sfarsit se testeaza valoarea acestei variabile si se afiseaza un mesaj adecvat;
P3.3.6 Verificarea primalitatii (3) Pseudocod prim=1; citeste n; pentru (i=2,n/2) executa{ daca (n%i==0)  prim=0 } daca (prim==1) {  scrie “e prim”  }  altfel { scrie “nu e prim” }
P3.3.6 Verificarea primalitatii (4) #include <conio.h> #include <iostream.h> int  main  ( void )   { unsigned   int  n, prim = 1 ; cout<<”N =  “; cin>>n; for   ( int  i = 2 ;i< = n / 2 ;i ++){ if   ( n % i == 0 ){ prim = 0 ; break; //atentiune } } if   ( prim )   { cout<<”Numarul “<<n<<” este prim”<<endl; } else   { cout<<”Numarul “<<n<<” nu este prim”<<endl; } return   0 ; }
P3.3.7 Filtru de esantionare (1) Exista o categorie de aplicatii de achizitie de semnal in care de la un senzor se culeg valori cu o anumita rata de achizitie. Se pune problema de a determina o valoare cat mai exacta. Metodologia este in felul urmator: Se culege un numar predefinit de esantioante (N_ES) Se determina simultan maximul si minimul din esantion (M si m); Se elimina din sirul de date valorile minime si maxime; Se face media setului de date ramas;
P3.3.7 Filtru de esantionare (2) Formalizare: Fie S={s 1 , s 2 , ... s N_ES } setul de date achizitionate; Fie M=max(S) si m=min(S); Vom defini S f ={{S}\M}\m; In final vom calcula  media lui S f ; Aceasta este valoare de interes.
P3.3.7 Filtru de esantionare (3) Pseudocod: contor=0; M=-UINT_MAX; m=UINT_MAX; cat timp (contor<=N_ES) executa { citeste nc; daca (nc>M) atunci M=nc; daca (nc<m) atunci m=nc; contor++; suma+=nc; } suma=suma-max-min; media=suma/(contor-2);
P3.3.7 Filtru de esantionare (4) Tema !!! De implementat in C/C++ pseudocodul de mai sus; Pentru a defini N_ES veti folosi o directiva  #define  astfel: #define N_ES 10 Nu se pune ;
Reprezentarea numerelor in calculator (1) Calculatorul foloseste notatia  binara , adica simboluri definite pe multimea B={0,1}; Se folosesc doua tipuri de numere:  intregi  (in virgula fixa) si  reale  (in virgula flotanta) [en. floating point – FP];
Reprezentarea numerelor in calculator (2) Reprezentarea numerelor in virgula fixa dedusa din forma zecimala ordinara a numerelor, in care numerele prezinta o virgula zecimala, la stanga acesteia este partea intreaga, iar la dreapta partea fractionara; fiecare pozitie are asociata o pondere, fapt pentru care se spune ca numerele sunt scrise intr-o ,,notatie ponderata'' (notatie pozitionala); N =x n-1 2 n-1 +x n-2 2 n-2 + ... +x 1 2 1 +x 0 x n-1  se numeste  bitul cel mai semnificativ  (MSB), iar x 0  se numeste  bitul cel mai putin semnificativ  (LSB); Astfel se pot deduce doua forme de scriere si utilizare: cu  MSB-first  sau  LSB-first , in citirea  de la stanga la dreapta .
Reprezentarea numerelor in calculator (3) Reprezentarea numerelor intregi cu semn Se stabileste in mod conventional ca bitul MSB sa reprezinte semnul; Tot prin conventie se stabileste ca MSB=0 inseamna numar pozitiv, iar MSB=1 numar negativ; !!! de completat Nu abordam FP (IEEE754)
P3.3.8 Transformarea dec2bin (1) Se citeste un numar natural. Sa se afiseze acel numar in binar. Se va folosi notatia LSB (least significant bit) first. Exemplu n=3 10  => 110 2 n=9 10  => 1001 2 Pentru rezolvare de va proceda la impartirea succesiva cu 2 si retinerea restului (acesta poate fi 0 sau 1). Impartirea se va opri atunci cand n=0
P3.3.8 Transformarea dec2bin (2) Pseudocod citeste n; cat timp (n<>0) executa { cb=n mod 2; //cb-cifra binara {0,1} afiseaza cb; n=n/2; }
P3.3.9 Transformarea dec2hex (1) Tema !!! Se citeste un numar natural. Sa se afiseze reprezentarea sa in format hexazecimal.  Reprezenatrea hexa foloseste urmatorul set de simboluri H={0, 1, 2, 3, 4, 5, 6, 7, 8, 9, A, B, C, D, E, F} Se vor face impartiri la 16, cu retinerea restului (ch=n mod 16).
P3.3.9 Transformarea dec2hex (2) Pentru afisarea corecta a literelor puteti folosi ceva similar cu: ch =  n % 16 ;   //obtinem restul impartirii la 16   if   ( ch> = 10 )   {  int  d = ch - 10 ;   //ne da distanta fata de 10 char  afis = 'A' + d;  //la codul lui 'A' adunam      // deplasamentul calculat mai sus // !!! mai gasiti o solutie pt calc lui afis cout<<afis; } else { cout<<ch;   //daca e <10 il afisam direct } ch =   n / 16 ;
P3.3.10 dec2bin cu operatii pe biti Se citeste un numar pe 8 biti ( short int ). Sa se afiseze reprezentarea sa in binar folosind doar operatii logice pe biti, de tipul  AND  si  shift -ari; int nr; cin>>nr; short   int  mask = 1 ;  // 00000001b = 0x01 for   ( int  i = 1 ;i< = 8 ;i ++){ short   int  u = n & mask;  // SI pe biti cout >>u; n>> = 1 ;  // echivalent n=n>>1; }
P3.3.11 dec2hex cu operatii pe biti Tema !!! Similar cu P3.3.10. Se va folosi o masca care sa permita pastrarea ultimilor 4 biti (o cifra binara) ( short   int  mask = 15 ; ) Se vor face deplasari la dreapta cu cate 4 biti ( n>> = 1 ; ) Veti afisa cate o cifra hexa sub forma a 4 biti pe cate o linie;
P3.3.12 Cate numere au  k  divizori Se citesc de la tastatura doua numere intregi:  n  si  k . Sa se calculeze si sa se afiseze cate dintre cele  n  numere au exact  k  divizori (1 este divizor pt. orice numar). Pseudocod: citeste n,k; pentru i=(1,n){ ndiv = 0; pentru d=(1,i/2) { daca (i/d == 0) ndiv++ } daca (ndiv == k){  afiseaza (“numarul “ i “corespunde”) } }
P3.3.13 Afisati divizorii unui numar Similar cu P3.3.12... dar mai simplu :) In bucla interioara in loc de a incrementa  ndiv  veti afisa respectivul divizor.

Curs5-PC-Cl9

  • 1.
    Curs 3 3.3.Structura repetitiva Alexandru IOVANOVICI
  • 2.
    3.3 Structura repetitivaSe foloseste pentru a implementa operatii care se repeta de mai multe ori in cadrul programului; Diferitii pasi difera foarte putin unul de celalalt prin niste marimi usor de pus identificat si reprezentat; Intotdeauna exista un sfarsit (! finitudine)
  • 3.
    P.3.3.1 Suma cifrelorunui numar (1) Se citeste un numar intreg n . Sa se calculeze si sa se afiseze suma cifrelor sale. Ex: n=1234 => S=1+2+3+4=10 Pseudocod: citeste n cat timp (n<>0) executa { u=n mod 10; S=S+u; } afiseza S
  • 4.
    P.3.3.1 Suma cifrelorunui numar (2) Citeste n n<>0 u=n mod 10; S=S+u n=n/10 Scrie S
  • 5.
    P.3.3.1 Suma cifrelorunui numar (3) #include <conio.h> #include <iostream.h> int main ( void ) { int n, S = 0 ; cout<<”N = “; cin>>n; while ( n != 0 ) { S = S + n % 10 ; n = n / 10 ; } cout<<”Suma cifrelor numarului “<<n<<” este “<<S; return 0 ; }
  • 6.
    P 3.3.2. Produsulcifrelor unui numar Tema !!! Similar cu P3.3.1; Atentie la initializarea lui P
  • 7.
    P3.3.3 Numere panala citirea unui nr. (1) Se citeste un numar intreg n de la tastatura. Mai apoi se citesc numere intregi pana la introducerea lui n . Sa se calculeze si sa se afiseze media aritmetica a numerelor introduse (fara n ); Atentie la tipul de date al mediei;
  • 8.
    P3.3.3 Numere panala citirea unui nr. (2) #include <conio.h> #include <iostream.h> int main ( void ) { int n,ct = 0 ; //in ct numar cate numere am float M; cout<<”Introduceti numarul cu rol de terminator : “; cin>>n; int nc = 0 ; //in nc voi pastra cate un numar citit pe rand while ( nc != n ) { cout<<”Numarul curent este : ”; cin>>nc; S = S + nc; ct ++ ; } cout<<”Media celor “<<ct - 1 <<” numere este “<<S /( ct - 1 ) ; return 0 ; }
  • 9.
    P3.3.4 Sirul luiFibbonaci (1) Sa se afiseze primii n termeni ai sirului lui Fibbonaci; SB se construieste in felul urmator: Primii doi termeni sunt 1 (Fb[1]=1, Fb[2]=1); Pentru urmatorii termeni este valabila regula: fiecare termen este egal cu suma dintre precedentul si anteprecedentul; (Fb[k] = Fb[k-1] + Fb[k-2]) Exemplu: Fb: 1, 1, 2, 3, 5, 8, 13, 21, 34, 55, ...
  • 10.
    P3.3.4 Sirul luiFibbonaci (2) #include <conio.h> #include <iostream.h> int main ( void ) { int tc; //termenul curent din sir int ta = 1 ; //termenul anterior din sir int taa = 1 ; //termenul ante-anterior din sir int n; cout<<”N = “; cin>>n; for ( int i = 3 ;i< n ;i ++){ tc = ta + taa; cout<<tc<<” “; taa = ta; ta = tc; } return 0 ; }
  • 11.
    P3.3.4 Maximul unuisir de numere (1) Se citesc numere naturale pana la introducerea lui zero (0); Sa se determine si sa se afiseze maximul dintre numerele citite; Exemplu: Sirul este: 2,1,3,4,2,7,8,0 Maximul este: 8
  • 12.
    P3.3.4 Maximul unuisir de numere (2) #include <conio.h> #include <iostream.h> #include <limits.h> int main ( void ){ unsigned int nc = 1 , max =- UINT_MAX; while ( nc != 0 ){ cout<< &quot;Introduceti un numar: &quot; ; cin>>nc; if ( nc>max ){ max = nc; } } cout<< &quot;Maximul este: &quot; <<max<<endl; return 0 ; }
  • 13.
    P3.3.5 Minimul unuisir de numere Tema !!! Problema P3.3.4 dar in loc de maxim se va calcula minimul; Consultati continutul fisierului limits.h
  • 14.
    P3.3.6 Verificarea primalitatii(1) Se citeste un numar natural . Sa se verifice si sa se afiseze daca acest numar este prim sau nu. Un numar este prim daca nu are drept divizori decat pe 1 si pe el insusi; Exemplu: Numarul 7: Este prim (nu are alti divizori); Numarul 8: Nu este prim (are divizori pe 2,4)
  • 15.
    P3.3.6 Verificarea primalitatii(2) Metodologia: Se citeste numarul; Se presupune ca numarul este prim (prim=1); Se parcurge cu un contor de la 2 la n/2 si se verifica daca este divizibil cu unul dintre acestea; In caz afirmativ variabila care indica primalitatea devine falsa (prim=0); La sfarsit se testeaza valoarea acestei variabile si se afiseaza un mesaj adecvat;
  • 16.
    P3.3.6 Verificarea primalitatii(3) Pseudocod prim=1; citeste n; pentru (i=2,n/2) executa{ daca (n%i==0) prim=0 } daca (prim==1) { scrie “e prim” } altfel { scrie “nu e prim” }
  • 17.
    P3.3.6 Verificarea primalitatii(4) #include <conio.h> #include <iostream.h> int main ( void ) { unsigned int n, prim = 1 ; cout<<”N = “; cin>>n; for ( int i = 2 ;i< = n / 2 ;i ++){ if ( n % i == 0 ){ prim = 0 ; break; //atentiune } } if ( prim ) { cout<<”Numarul “<<n<<” este prim”<<endl; } else { cout<<”Numarul “<<n<<” nu este prim”<<endl; } return 0 ; }
  • 18.
    P3.3.7 Filtru deesantionare (1) Exista o categorie de aplicatii de achizitie de semnal in care de la un senzor se culeg valori cu o anumita rata de achizitie. Se pune problema de a determina o valoare cat mai exacta. Metodologia este in felul urmator: Se culege un numar predefinit de esantioante (N_ES) Se determina simultan maximul si minimul din esantion (M si m); Se elimina din sirul de date valorile minime si maxime; Se face media setului de date ramas;
  • 19.
    P3.3.7 Filtru deesantionare (2) Formalizare: Fie S={s 1 , s 2 , ... s N_ES } setul de date achizitionate; Fie M=max(S) si m=min(S); Vom defini S f ={{S}\M}\m; In final vom calcula media lui S f ; Aceasta este valoare de interes.
  • 20.
    P3.3.7 Filtru deesantionare (3) Pseudocod: contor=0; M=-UINT_MAX; m=UINT_MAX; cat timp (contor<=N_ES) executa { citeste nc; daca (nc>M) atunci M=nc; daca (nc<m) atunci m=nc; contor++; suma+=nc; } suma=suma-max-min; media=suma/(contor-2);
  • 21.
    P3.3.7 Filtru deesantionare (4) Tema !!! De implementat in C/C++ pseudocodul de mai sus; Pentru a defini N_ES veti folosi o directiva #define astfel: #define N_ES 10 Nu se pune ;
  • 22.
    Reprezentarea numerelor incalculator (1) Calculatorul foloseste notatia binara , adica simboluri definite pe multimea B={0,1}; Se folosesc doua tipuri de numere: intregi (in virgula fixa) si reale (in virgula flotanta) [en. floating point – FP];
  • 23.
    Reprezentarea numerelor incalculator (2) Reprezentarea numerelor in virgula fixa dedusa din forma zecimala ordinara a numerelor, in care numerele prezinta o virgula zecimala, la stanga acesteia este partea intreaga, iar la dreapta partea fractionara; fiecare pozitie are asociata o pondere, fapt pentru care se spune ca numerele sunt scrise intr-o ,,notatie ponderata'' (notatie pozitionala); N =x n-1 2 n-1 +x n-2 2 n-2 + ... +x 1 2 1 +x 0 x n-1 se numeste bitul cel mai semnificativ (MSB), iar x 0 se numeste bitul cel mai putin semnificativ (LSB); Astfel se pot deduce doua forme de scriere si utilizare: cu MSB-first sau LSB-first , in citirea de la stanga la dreapta .
  • 24.
    Reprezentarea numerelor incalculator (3) Reprezentarea numerelor intregi cu semn Se stabileste in mod conventional ca bitul MSB sa reprezinte semnul; Tot prin conventie se stabileste ca MSB=0 inseamna numar pozitiv, iar MSB=1 numar negativ; !!! de completat Nu abordam FP (IEEE754)
  • 25.
    P3.3.8 Transformarea dec2bin(1) Se citeste un numar natural. Sa se afiseze acel numar in binar. Se va folosi notatia LSB (least significant bit) first. Exemplu n=3 10 => 110 2 n=9 10 => 1001 2 Pentru rezolvare de va proceda la impartirea succesiva cu 2 si retinerea restului (acesta poate fi 0 sau 1). Impartirea se va opri atunci cand n=0
  • 26.
    P3.3.8 Transformarea dec2bin(2) Pseudocod citeste n; cat timp (n<>0) executa { cb=n mod 2; //cb-cifra binara {0,1} afiseaza cb; n=n/2; }
  • 27.
    P3.3.9 Transformarea dec2hex(1) Tema !!! Se citeste un numar natural. Sa se afiseze reprezentarea sa in format hexazecimal. Reprezenatrea hexa foloseste urmatorul set de simboluri H={0, 1, 2, 3, 4, 5, 6, 7, 8, 9, A, B, C, D, E, F} Se vor face impartiri la 16, cu retinerea restului (ch=n mod 16).
  • 28.
    P3.3.9 Transformarea dec2hex(2) Pentru afisarea corecta a literelor puteti folosi ceva similar cu: ch = n % 16 ; //obtinem restul impartirii la 16 if ( ch> = 10 ) { int d = ch - 10 ; //ne da distanta fata de 10 char afis = 'A' + d; //la codul lui 'A' adunam // deplasamentul calculat mai sus // !!! mai gasiti o solutie pt calc lui afis cout<<afis; } else { cout<<ch; //daca e <10 il afisam direct } ch = n / 16 ;
  • 29.
    P3.3.10 dec2bin cuoperatii pe biti Se citeste un numar pe 8 biti ( short int ). Sa se afiseze reprezentarea sa in binar folosind doar operatii logice pe biti, de tipul AND si shift -ari; int nr; cin>>nr; short int mask = 1 ; // 00000001b = 0x01 for ( int i = 1 ;i< = 8 ;i ++){ short int u = n & mask; // SI pe biti cout >>u; n>> = 1 ; // echivalent n=n>>1; }
  • 30.
    P3.3.11 dec2hex cuoperatii pe biti Tema !!! Similar cu P3.3.10. Se va folosi o masca care sa permita pastrarea ultimilor 4 biti (o cifra binara) ( short int mask = 15 ; ) Se vor face deplasari la dreapta cu cate 4 biti ( n>> = 1 ; ) Veti afisa cate o cifra hexa sub forma a 4 biti pe cate o linie;
  • 31.
    P3.3.12 Cate numereau k divizori Se citesc de la tastatura doua numere intregi: n si k . Sa se calculeze si sa se afiseze cate dintre cele n numere au exact k divizori (1 este divizor pt. orice numar). Pseudocod: citeste n,k; pentru i=(1,n){ ndiv = 0; pentru d=(1,i/2) { daca (i/d == 0) ndiv++ } daca (ndiv == k){ afiseaza (“numarul “ i “corespunde”) } }
  • 32.
    P3.3.13 Afisati divizoriiunui numar Similar cu P3.3.12... dar mai simplu :) In bucla interioara in loc de a incrementa ndiv veti afisa respectivul divizor.