start     Articole     Despre mine     Contact     Cursul ABCprog    

Cum faci repetari in C

Daca ai parcurs lectiile de introducere in programare, stii deja instructiunea “while”. Cred ca nu te va surprinde sa afli ca while-ul din C este foarte similar (ca sa nu zic “chiar la fel”) cu cel pe care il stii.

In plus fata de el, vei mai invata in lectia asta instructiunile “do … while” si “for”, care sunt ambele foarte asemanatoare cu “while”.

Dar hai sa luam lucrurile pe rand.

Instructiunea “while”

O stii deja. Stii ca ea e “motorul” programarii. Programele pe care le-ai scris pana aici in C au fost programe “de jucarie”.

Chiar daca poti lua decizii, nu poti face nimic serios intr-un program decat atunci cand ai posibilitatea sa repeti o serie de instructiuni de un numar (cunoscut in avans sau nu) de ori.

Iar instructiunea while iti ofera aceasta posibilitate (asa cum ai vazut in Abecedar).

N-are sens sa repet ce stii deja, asa ca o voi pune direct la treaba intr-un program care va afisa pe ecran (ca text in terminalul de comenzi, ca si pana acum) in ordine inversa cifrele unui numar introdus de la tastatura:

#include <stdio.h>
int main()
{
	int n;
	printf("Scrie un numar format din maxim 6 cifre: ");
	scanf("%d", &n);
	printf("Cifrele numarului (in ordine inversa) sunt:\n");
	while (n != 0)
	{
		printf("%d", n%10);
		n = n/10;
	}
	printf("\n");
	return 0;
}

Testeaza-l, te rog. Merge, asa-i?…

Sigur ca merge. Doar ca pentru numarul 0 programul nu afiseaza nimic!(Ruleaza din nou programul, scrie 0 si apasa “Enter”. Ce apare pe ecran?… Nu apare nimic, nu-i asa?)

Bineinteles ca nu afiseaza nimic atunci cand numarul introdus a fost 0, fiindca blocul de instructiuni din while nu se executa niciodata (deoarece conditia (n != 0) e falsa atunci cand in variabila n se gaseste valoarea 0).

Te poti gandi la o solutie pentru a remedia problema asta? (Stiu ca poti. Fa-o, te rog. Ia o pauza de la acest articol, deschide Code::Blocks-ul si apuca-te de treaba joaca.)

Eu o sa-ti dau acum o alta solutie — cu instructiunea do while.

Instructiunea “do while”

Daca “while” e un fel de “cat timp e adevarata conditia, repeta instructiunile”, “do while” e un fel de “repeta instructiunile, cat timp e adevarata conditia”.

Deci singura diferenta dintre ele e ca in “do while” conditia e verificata dupa ce blocul de instructiuni a fost executat cel putin o data.

Asta inseamna ca problema din programul anterior o puteam remedia prin simpla inlocuire a lui “while” cu “do while”:

#include <stdio.h>
int main()
{
	int n;
	printf("Scrie un numar format din maxim 6 cifre: ");
	scanf("%d", &n);
	printf("Cifrele numarului (in ordine inversa) sunt:\n");
	do {
		printf("%d", n%10);
		n = n/10;
	} while (n != 0);
	printf("\n");
	return 0;
}

Formatul generic al unei instructiuni “do while” e, asa cum banuiesc ca ai intuit, urmatorul:

do
    Instructiuni
while (Conditie);

(Cu mentiunea ca “Instructiuni” poate fi o singura instructiune sau un bloc format din mai multe instructiuni plasate intre acolade.)

Bineinteles ca puteai obtine acelasi efect cu un “while”:

Instructiuni
while (Conditie)
    Instructiuni

Era mai dificil, insa, caci trebuia sa scrii de doua ori instructiunea sau secventa de instructiuni pe care o doreai repetata.

In schimb, daca folosesti “do while” o scrii o singura data. Deci am putea spune ca instructiunea “do while” nu are in spate vreun concept nou de programare, ci e doar un soi de “artificiu” sintactic ce ne ajuta sa scriem programe mai scurte.

Instructiunea “for”

Si tot din categoria asta a simplificarilor sintactice, da-im voie sa iti prezint o instructiune foarte utilizata in programele scrise in limbajul C (si nu numai) — instructiunea “for”.

E destul de dificil de explicat clar in cuvinte ce face instructiunea “for”, asa ca las urmatorul exemplu sa “vorbeasca”:

#include <stdio.h>
int main()
{
	int n;
        int i;
	printf("Scrie un numar natural (preferabil intre 1 si 10): ");
	scanf("%d", &n);
	printf("Super! Acum hai sa numaram de la 1 la %d:\n", n);
	for (i=1; i<=n; i=i+1)
        {
		printf("%d\n", i);
	}
	return 0;
}

Ahaa, deci!… Da, inseamna ca instructiunea “for” doar te ajuta sa scrii mai compact portiuni de cod in care ai nevoie ca o variabila sa ia pe rand valori dintr-un sir de numere.

In cazul exemplului de mai sus, variabila i ia pe rand valori din sirul 1, 2, 3, 4, 5, …, n.

Dar puteai face asta si cu instructiunea while, nu-i asa? (Bineinteles ca da — doar asa ai facut in Abecedar, nu?)

...
i = 1;
while (i <= n)
{
        printf("%d\n", i);
        i = i+1;
}
...

Avantajul utilizarii instructiunii “for” e ca scrii mai putin si mai ales ca instructiunea prin care treci la urmatoarea valoare din sirul de numere (adica, in acest caz, instructiunea “i = i + 1”) o vezi din prima cand citesti codul sursa, fara sa fie nevoie sa te uiti dupa ea pe la finalul blocului de instructiuni din “while”.

Cu putin antrenament vei ajunge sa citesti “for (i=1; i<=n; i=i+1)” ca “pentru i luand valori de la 1 la n (din 1 in 1)”.

Dar “for”-ul din C nu e limitat doar la utilizari de acest gen, ci poate fi folosit pentru a compacta instructiuni “while” generice. (Asta il face, pe de o parte, mai puternic decat “for”-urile din alte limbaje de programare; pe de alta parte, insa, il face mai dificil de inteles pentru incepatori.)

Hai sa vedem cum arata o instructiune “for” generica:

for (Expresie1; Expresie2; Expresie3)
    Instructiuni

Acelasi efect il poti obtine cu “while”, astfel:

Expresie1;
while (Expresie2)
{
    Instructiuni
    Expresie3
}

Nu as vrea sa intru acum in detalii a caror cunoastere nu iti va imbunatati aproape deloc abilitatile de programare in C, asa ca ne putem opri aici cu explicatiile legate de instructiunea “for” din limbajul C.

Inainte de a incheia, insa, lectia asta dedicata instructiunilor de repetitie din C as vrea sa iti pomenesc doua instructiuni speciale care au sens doar in contextul acestor repetitii. (Se poate si fara ele, dar cu ajutorul lor codul sursa poate sa arate mai clar.)

Instructiunile “break” si “continue”

Incerc sa explic lucrurile cat mai generic, asa ca hai sa vedem cate un exemplu generic de utilizare pentru fiecare dintre aceste doua instructiuni:

// Exemplu generic pentru "break"
Instructiune_de_repetitie
{
    Instructiuni
    break;
    Alte_instructiuni
}

// Exemplu generic pentru "continue"
Instructiune_de_repetitie
{
    Instructiuni
    continue;
    Alte_instructiuni
}

In cazul primului exemplu de mai sus, secventa Alte_instructiuni nu se mai executa, ci la intalnirea lui “break” se iese din respectiva instructiune de repetitie (indiferent daca conditia de repetare e adevarata sau nu).

Instructiunea “continue” seamana un pic cu “break” — in sensul ca la intalnirea ei executarea blocului de instructiuni se intrerupe (adica Alte_instructiuni nu se mai executa), insa nu se iese automat din instructiunea de repetitie, ci se verifica conditia de repetare.

Altfel spus, “break” sare la finalul instructiunii de repetare in care se gaseste, iar “continue” sare la reverificarea conditiei de repetare din instructiunea de repetare in care se gaseste.

Concluzie

Instructiunile de repetare sunt “motorul” programarii. Nu doar in limbajul de programare C, ci in practic orice limbaj (caci majoritatea limbajelor de programare utilizate in practica sunt bazate pe paradigma de programare imperativa).

(Nu te ingrijora daca nu intelegi acum ce inseamna aia “paradigma de programare” — am vorbit un pic despre asta in Abecedar, dar poti trece mai departe si fara sa intelegi acest concept.))

Repetarea e baza prin care se poate realiza practic automatizarea, care e esenta motivatiei de a programa calculatoare sa faca lucruri. Calculatoarele nu stiu sa faca lucruri foarte complicate, ci stiu sa faca doar cateva lucruri (in esenta extrem de simple) — dar acele lucruri le fac cu o viteza extraordinar de mare si, in plus, au abilitatea asta de a repeta actiuni in functie de indeplinirea unor conditii. Combinand asta cu abilitatea de a salva valori intr-o memorie, calculatoarele devin astfel niste “robotei” ce pot executa practic orice sarcina ce le poate fi exprimata intr-o maniera neambigua.

Concluzia concluziei 🙂 e ca te rog sa nu treci peste lectia asta pana cand nu te joci serios cu instructiunile invatate aici. (Si chiar te invit sa le “cuibaresti” unele in altele si sa vezi ce se intampla.)

Spune-mi, te rog, cum ti se pare pana aici tutorialul de C si daca (if) explicatiile sunt pe intelesul tau. (Sau (else) spune-mi unde simti ca ar trebui sa iti explic mai clar.)

 

Alatura-te celor peste 7800 de oameni din armata noastra de creiere cu muschi si vei primi testul care iti va spune daca ai sau nu minte de programator.

In plus, vei fi mereu la curent cu tot ce pun la cale.

(Vei primi automat un email in care ti se va solicita acordul de prelucrare a datelor cu caracter personal.)

 

Cu drag,

Florin Bîrleanu





Loading Facebook Comments ...