Podstawy
programowania I
Wykład nr 8
Instrukcje obliczeń cyklicznych. Pętla for, while, do..while()
autor: dr inż. Michał Łabowski
▪ michal.labowski@wat.edu.pl
▪ www.mlabowski.wel.wat.edu.pl
wersja 1.0
Pętle w C++
W języku C i C++ występują trzy rodzaje pętli:
• for (czytaj: dla)
• while (czytaj: dopóki lub tak długo jak)
• do while (czytaj: rób… dopóki) Pętla for:
• stosowana wtedy, gdy dokładnie wiadomo ile razy pętla ma się wykonać,
• najbardziej odporna na przypadkowe błędy programisty Składnia:
for (instrukcja_inicjujaca; wyrazenie_warunkowe; instrukcja_kroku) {
instrukcje;
}
instrukcja_inicjujaca – najczęściej operacja przypisania początkowej wartości iteratorowi, np. int i = 0. Obiekt zdefiniowany w instrukcji inicjującej istnieje tylko w ramach pętli for (to zmienna automatyczna o zasięgu blokowym).
wyrazenie_warunkowe – pętla (czyli instrukcje zawarte pomiędzy klamrami) wykonuje się tak długo, jak wyrażenie to ma wartość true, np. i < 10
instrukcja_kroku – instrukcja powodująca zmianę wartości iteratora, np. ++i Te trzy elementy muszą być rozdzielone średnikami ;
Składnia nieskończonej pętli for: for(;;);
Pętle w C++
3
instrukcja_1;
for (instrukcja_inicjujaca; wyrazenie_warunkowe; instrukcja_kroku) {
instrukcja_2;
}
instrukcja_3;
for Zadanie 1. Napisz program, który za pomocą pętli for dla wartości x z przedziału <0, 10> wyznaczy wartość funkcji y = 3x.
for
5
Zadanie 1. Napisz program, który za pomocą pętli for dla wartości x z przedziału <0, 10> wyznaczy wartość funkcji y = 3x.
Nr linii Opis
9-13 Pęta for. Pierwszy obieg pętli jest szczególny, ponieważ na jego początku wykonywana jest instrukcja inicjująca. Dalszy przebieg jest już standardowy: wykonywane jest sprawdzenie wyrażenia warunkowego, jeśli jest ono spełnione wykonują się instrukcje (linie 11, 12), a na koniec instrukcja kroku. Kolejne obiegi pętli rozpoczynają się od sprawdzenia warunku, następnie mogą być wykonane instrukcje i krok.
while Pętla while:
• stosowana wtedy, gdy nie wiadomo z góry ile razy pętla ma się wykonać (np.
liczbę tę wprowadza użytkownik programu)
• podatna na błędy programisty, ponieważ instrukcja_inicjujaca, wyrazenie_warunkowe oraz instrukcja_kroku nie znajdują się w jednej linii, więc łatwo o którejś z nich zapomnieć.
Składnia:
instrukcja_inicjujaca;
while (wyrazenie_warunkowe) {
instrukcje;
instrukcja_kroku;
}
Cechą charakterystyczną pętli while jest to, że instrukcje mogą nigdy się nie wykonać, jeśli wyrazenie_warunkowema początkowo wartość false.
Składnia nieskończonej pętli while:
while(true) {
instrukcje;
}
while
7
instrukcja_inicjujaca;
while (wyrazenie_warunkowe) {
instrukcje2;
}
instrukcje3;
while
8
Zadanie 2. Napisz program, który za pomocą pętli while dla wartości x z przedziału
<0, 10> wyznaczy wartość funkcji y = 3x.
Nr linii Opis
9 instrukcja inicjująca
10-15 Pętla while. Na początku pętli sprawdzane jest wyrażenie warunkowe (linia 10), jeśli jest ono spełnione wykonują się instrukcje z linii 12-14, gdzie linia 14 to instrukcja kroku.
do while
9
Pętla do while:
• stosowana wtedy, gdy nie wiadomo z góry ile razy pętla ma się wykonać (np.
liczbę tę wprowadza użytkownik programu) – podobnie jak pętla while,
• podatna na błędy programisty, ponieważ instrukcja_inicjujaca, wyrazenie_warunkowe oraz instrukcja_kroku nie znajdują się w jednej linii, więc łatwo o którejś z nich zapomnieć – podobnie jak pętla while,
Składnia:
instrukcja_inicjujaca;
do {
instrukcje;
instrukcja_kroku;
} while (wyrazenie_warunkowe);
Cechą charakterystyczną pętli while jest to, że instrukcje muszą się wykonać co najmniej raz, nawet jeśli wyrazenie_warunkowe ma początkowo wartość false.
Sprawdzenie warunku znajduje się bowiem po instrukcjach (w pętli while – przed).
Składnia nieskończonej pętli do while:
do {
instrukcje;
} while(true);
do while instrukcja_inicjujaca;
do {
instrukcje_1;
} while (wyrazenie_warunkowe);
instrukcja_2;
do while
11
Zadanie 3. Napisz program, który za pomocą pętli do while dla wartości x z przedziału <0, 10> wyznaczy wartość funkcji y = 3x.
Nr linii Opis
9 instrukcja inicjująca
10-15 Pętla do while. Po wejściu do pętli najpierw wykonywane są instrukcje z linii 12-14, a dopiero później sprawdzane jest wyrażenie warunkowe (linia 15),
14 instrukcja kroku.
break Instrukcja break powoduje natychmiastowe przerwanie wykonywania pętli for, while, do while, jak również poznanej wcześniej instrukcji switch [1]. W przypadku pętli zagnieżdżonych break powoduje przerwanie pętli, w której zostało wywołane.
Zadanie 4. Zmodyfikuj program z zadania 1, tak aby wyznaczanie i wyświetlanie wartości zatrzymało się dla x równego 4. Wykorzystaj instrukcję break.
break
13
Nr linii Opis
12 sprawdzenie warunku, czy x jest równy 4
14 jeśli warunek z linii 12 jest spełniony, wówczas wykonywana jest instrukcja break, za sprawą której następuje wyjście z pętli for i przejście do następującej po niej linii kodu, czyli linii nr 17.
continue Instrukcja continue powoduje zaniechanie wykonywania dalszej części instrukcji w pętli – przerywany jest aktualny obieg pętli, następuje wykonanie instrukcji kroku i sprawdzenie warunku, a jeśli jest on spełniony pętla wykonuje się dalej.
Zadanie 5. Zmodyfikuj program z zadania 1, tak aby nie wyświetlono wyników dla x równego 4. Wykorzystaj instrukcję continue.
continue
15
Nr linii Opis
11 sprawdzenie warunku, czy x jest równy 4
13 jeśli warunek z linii 11 jest spełniony, wówczas wykonywana jest instrukcja continue, za sprawą której następuje przerwanie aktualnego wykonania pętli, x jest zwiększany o jeden, sprawdzany jest warunek (x<=10), a ponieważ jest on spełniony, wykonywane są ponownie instrukcje zawarte w nawiasach klamrowych (linie 9 -17)
*pętle zagnieżdżone Zagnieżdżenie pętli polega na umieszczeniu jednej pętli w drugiej - dla pętli for wygląda to następująco:
for (instrukcja_inicjujaca1; wyrazenie_warunkowe1; instrukcja_kroku1) {
instrukcje1;
for (instrukcja_inicjujaca2; wyrazenie_warunkowe2; instrukcja_kroku2) {
instrukcje2;
} }
Załóżmy, że pętla zewnętrza wykonuje się w-krotnie, a pętla wewnętrza k-krotnie.
Istota zagnieżdżenia w powyższym przykładzie polega na tym, że w każdym pojedynczym obiegu pętli zewnętrznej wykonają się jednokrotnie instrukcje1 oraz pętla wewnętrza, przy czym pętla wykona się od początku (instrukcji_inicjującej2) aż do niespełnienia wyrażenia_warunkowego2, czyli k-krotnie (instrukcje2 wykonają się k-krotnie). W tej sytuacji po wyjściu z obu pętli instrukcje2 wykonają się łącznie w*k-krotnie (dla każdego w, po k-razy).
Przydatne przy przetwarzaniu tablic n-wymiarowych.
Pętla zewn. Pętla wew.
liczby pseudolosowe
17
Liczby losowe w C++:
• Liczby „losowe” generowane przez komputer wyznaczane są na podstawie przyjętego algorytmu (wzoru generacyjnego), więc są przewidywalne. Z tego powodu nazywane są liczbami pseudolosowymi.
• W C++ za generację takich liczb odpowiada m.in. funkcja rand(), która zwraca liczbę całkowitą z przedziału od 0 do RAND_MAX (wykorzystywany jest równomierny rozkład prawdopodobieństwa). Makro RAND_MAX wynosi co najmniej 32 767.
• W celu zapewnienia zmienności generowanych liczb pomiędzy uruchomieniami programu konieczna jest inicjalizacja generatora liczbą o charakterze zmiennym, do czego dobrze nadaje się aktualny czas. Za inicjalizację odpowiada funkcja srand().
• deklaracje funkcji srand() i rand() znajdują się w pliku nagłówkowym cstdlib
Zadanie 6. Napisz program, który wygeneruje trzy liczby losowe: pierwsza z przedziału od 0 do 99, druga z przedziału od 1 do 100, trzecia z przedziału od 1985 do 2014.
liczby pseudolosowe
Nr linii Opis
12 plik nagłówkowy dla funkcji time() zwracającej aktualny czas (poczytaj jej opis na stronie http://www.cplusplus.com/reference/)
7 inicjalizacja generatora wartością aktualnego czasu
8 Wynikiem dzielenia modulo X%Y jest liczba z przedziału <0, Y-1>, zatem dzielenie rand() % 100 zwraca liczbę z przedziału <0, 99>
9 Przesunięcie przedziału o 1, czyli <0, 99> + 1 --> <1, 100>
10 Przesunięcie przedziału o 1985, czyli <0, 29> + 1985 --> <1985, 2014>
19
Literatura:
[1] Grębosz J., Opus Magnum C++, Helion, Gliwice, 2018
[2] Prata S., Język C++ Szkoła programowania, Helion, Gliwice, 2013 [3] Prata S., Język C Szkoła programowania, Helion, Gliwice, 2012