Ten materiał poruszy jedną z najbardziej fundamentalnych konstrukcji programistycznych bez względu na język, w jakim piszesz kod 😱! Bez niej, nie byłoby szans na wykonywanie wielu tych samych instrukcji naraz tyle razy, ile się chce 🔥! Tą rzeczą w programowaniu jest pętla "for" 💥! Wyjaśniam co to takiego, jaką zazwyczaj przyjmuje formę w kodzie (oraz na jakie inne możesz natrafić) oraz kiedy najlepiej użyć właśnie tej pętli, a nie innej 🚀. Nie zastanawiaj się, tylko wchodź i czytaj 😄!

PĘTLA "FOR" W PROGRAMOWANIU JAKO NIEZBĘDNY ELEMENT!

Artykuł dotyczy programowania ogólnie, niezwiązanego z jakimkolwiek konkretnym językiem programowania, więc spróbuję podejść do tego uniwersalnie starając się "dotknąć" każdego wątku związanego z pętlą "for" ℹ️. Najpierw krótko opiszę czym jest pętla "for" i przedstawię jej najbardziej podstawową budowę. Następnie pokażę bardzo prosty przykład użycia w praktyce oraz w jakich sytuacjach najlepiej zastosować tę pętlę, a nie inną (bo jest jeszcze "while" i "do while" 🙂). A na sam koniec opowiem Ci na jakie możesz natrafić inne postacie tej samej pętli występujące w niektórych językach wysokiego poziomu ❤️.

Mamy co wyjaśniać, więc zaczynamy 😉!

CZYM JEST PĘTLA "FOR" W PROGRAMOWANIU?

Pętla "for" jest jedną z konstrukcji obok pętli "while" i "do while" przeznaczonych do wielokrotnego wykonywania pewnego ciągu instrukcji 🔁. Jest mnóstwo sytuacji, w których zajdzie potrzeba stworzyć coś, co będzie wymagać powtórzenia dokładnie tych samych czynności określoną liczbę razy. Właśnie wtedy sięgamy po pętlę, a to czy "for", czy inną, to już zależy od określonego problemu.

W tym artykule skupiamy się na pętli "for" i ona jest stworzona do wykonywania instrukcji pewną dokładną (wiadomą) liczbę razy ✅. To oznacza, że pasuje idealnie do obsługi uporządkowanych struktur danych, w których do każdego elementu można się przedostać używając indeksu, czyli liczby określającej jej "numer porządkowy" liczony od zera (np. tablica) 🤩. Przy użyciu tzw. "zmiennej iteracyjnej", która znajduje się w obrębie pętli "for", możemy się nią posłużyć do "przemieszczania się" element po elemencie ▶️.

KIEDY NAJLEPIEJ UŻYĆ PĘTLI "FOR" W PROGRAMOWANIU?

Postać pętli "for" posiada miejsce dla zmiennej iteracyjnej, z której możemy korzystać w jej bloku instrukcji i stąd najlepiej użyć tej pętli w 2 przypadkach 👇:

  1. gdy coś powinno się wykonać wiadomą liczbę razy,
  2. gdy potrzeba obsłużyć każdy element dowolnej uporządkowanej struktury danych (np. tablicy).

Istnieje też przypadek, w którym będziemy chcieli, aby pętla wykonała coś wielokrotnie, przy czym nie jesteśmy w stanie stwierdzić ile razy (np. szukanie drogi do wyjścia)❓. Wtedy dużo lepiej będzie pasować użycie pętli "while" 🎯. Ona składa się wyłącznie z warunku wejścia i lepiej pasuje do sytuacji, w których nie potrzeba dodatkowej zmiennej.

Tak brzmi ogólny zestaw informacji o pętli "for", a teraz przyjrzymy się jej strukturze w kodzie 👀!

JAK UTWORZYĆ PĘTLĘ "FOR" W PROGRAMOWANIU?

Obecnie występuje kilka różnych form pętli "for", lecz taka najbardziej podstawowa wywodzi się z języka C i wygląda następująco 👇:

for ([zmienna iteracyjna]; [warunek wejścia]; [modyfikacja zmiennej iteracyjnej po jednokrotnym wykonaniu bloku)
{
	[instrukcje]
}

Tradycyjna postać pętli "for" składa się z trzech osobnych części 👇:

  1. inicjalizacja zmiennej iteracyjnej (zmiennej występującej tylko w obrębie pętli "for"),
  2. zdefiniowanie warunku wejścia (warunek powstały z operatorów relacyjnych określający kiedy pętla powinna być przerwana),
  3. modyfikacja zmiennej iteracyjnej (instrukcja modyfikująca wartość zmiennej iteracyjnej po wykonaniu jednego pełnego obiegu pętli).

Zobacz, że każdą z tych części oddzielamy średnikiem ⚠️. To jest bardzo ważne, aby się nie pomylić i nie wstawić przecinka z przyzwyczajenia, ponieważ stanowi to obowiązkowy element składniowy, bez którego kompilator (bądź interpreter) zgłosi błąd ❌. To akurat dotyczy języka C i zasady budowy pętli ostatecznie zależą od języka programowania ℹ️.

Pętla "for" działa w sposób następujący 👇:

  • przejście do inicjalizacji zmiennej iteracyjnej (1),
  • zbadanie warunku wejścia czy jest spełniony (2),
    • jeżeli jest:
      • wykonanie wszystkich instrukcji zawartych w środku,
      • przejście do modyfikacji zmiennej iteracyjnej (3),
      • powrót do punktu zbadania warunku wejścia (2),
    • jeżeli nie jest, to przerwanie pętli i przejście do dalszych instrukcji.

Opiszę Ci teraz dokładniej jak rozumieć każdą z tych trzech części w nawiasie ⏩!

INICJALIZACJA ZMIENNEJ ITERACYJNEJ

Zaraz po nawiasie otwierającym zawsze zaczynamy od utworzenia zmiennej rejestrującej bieżącą wartość, która będzie rosnąć lub maleć co każdą iterację (jedno powtórzenie danej pętli ℹ️). Zazwyczaj nadajemy jej nazwę "i" (mała litera 'i' jako skrót od "index") i pochodzi od indeksu jakim się posługujemy do obsługi pojedynczych elementów tablicy, natomiast nie musi taka być 🙂. Z tego samego powodu, najczęściej podaje się typ "int" czyli liczbę całkowitą, natomiast i w tym przypadku możemy dać co chcemy (o ile to ma sens) 😊.

Zmienna iteracyjna najczęściej oznacza aktualny indeks elementu (choć może też oznaczać zwyczajnie liczbę wykonanych powtórzeń) i występuje po to, aby móc w środku pętli "for" swobodnie przedostawać się do poszczególnych elementów dowolnej uporządkowanej struktury danych 🎯. To jest podstawowe zastosowanie, natomiast możemy skorzystać z niej w inny sposób i na przykład wypisywać jaką wartość przyjmuje w danej chwili, i wtedy w ogóle wykracza poza jakiekolwiek elementy 👍.

Pętla "for" posiada swoje miejsce na zmienną przechowującą jakąś wartość, natomiast kontekst i sposób użycia tej wartości zależy tylko od nas, więc warto pamiętać, że nie musimy się ograniczać jedynie do tablic 😉.

A teraz drugi element pętli "for" 2️⃣!

ZDEFINIOWANIE WARUNKU WEJŚCIA

Pętla ma za zadanie wykonać coś określoną liczbę razy, lecz któregoś razu chcielibyśmy, aby przestała to robić i aby program mógł przejść dalej 😅. W tym celu, w drugiej części pętli określa się warunek, taki sam jak w instrukcjach warunkowych, czyli co musi się stać, aby trzeba było stwierdzić, że "OK, tu jest potrzebna jeszcze jedna powtórka" 💡.

Warunek tworzymy z użyciem operatorów relacyjnych i ewentualnie logicznych, jeśli chcemy zbudować warunek złożony (np. koniunkcja czy alternatywa) 🙂. To jest przykład 👇:

i < 10

To będzie oznaczać "opuszczenie" pętli, gdy zmienna iteracyjna "i" przekroczy wartość 10 (stanie się większa bądź równa) ↩️. Druga często stosowana postać, to uzależnienie od rozmiaru struktury danych, po której się poruszamy. Wtedy albo korzystamy wprost z informacji o liczbie elementów 👇:

i < arrayLength

albo poprzez funkcję zwracającą wartość logiczną ("bool"), która bada czy są w strukturze danych jeszcze jakieś elementy (tak się robi choćby w kolejce ℹ️) 👇:

!isEmpty()

Także jak widzisz, nie ma żadnej "jedynej słusznej drogi". Wszystko zależy od problemu, pętli jakiej użyjemy i struktur danych 😉.

Możemy też wstawić stałą wartość "true" lub "false", jednak to nie będzie miało żadnego sensu 😅.

Przechodzimy do poznania trzeciej i ostatniej zarazem części pętli "for" 3️⃣!

MODYFIKACJA ZMIENNEJ ITERACYJNEJ

Na samym końcu tworzenia pętli "for" mamy miejsce do określenia w jaki sposób zmienna iteracyjna ma być modyfikowana co każdą iterację (powtórzenie) 👍. Zazwyczaj ujrzysz taką postać 👇:

i++

To jest tzw. "inkrementacja", a dokładniej "postinkrementacja" ℹ️. Więcej informacji na jej temat znajdziesz w załączonym artykule, a jednym zdaniem chodzi o zwiększenie wartości zmiennej typu całkowitoliczbowego dokładnie o jeden ➕. To jest kolejne nawiązanie historyczne do pierwotnego zastosowania pętli "for", czyli obsługi elementów tablicy jeden po drugim 😊. Zależnie od "kierunku" obsługi pojedynczych elementów, możesz też spotkać się z "dekrementacją", czyli odejmowaniu od licznika całkowitoliczbowego dokładnie o jeden 👇:

i--

Natomiast powtarzam po raz kolejny: to nie jest jedyny dopuszczalny zapis! Jeżeli zmienna iteracyjna nie ma nic wspólnego z odwoływaniem się do elementów dowolnej uporządkowanej struktury danych i jest typu zmiennoprzecinkowego (przyjmuje "float" lub "double" ℹ️), możemy na przykład podnosić o pół 👇:

i += 0.5f

Przeważnie jednak nie stosuje się modyfikowania co ułamek i częściej wykonuje się mnożenie danej wartości całkowitoliczbowej przez dany ułamek (jeżeli już jest potrzebne), więc w miarę możliwości dąż do stosowania wyłącznie tradycyjnej formy modyfikowania, czyli o jeden do góry lub do dołu 👍.

Wyjaśniliśmy sobie całą postać pętli "for" z uwzględnieniem wszystkich jej trzech części ✔️. Warto również napomknąć o tym, że o ile język programowania na to pozwala, możesz pominąć którąkolwiek z tych części poprzestając tylko na wstawieniu samego średnika 👇:

for (; i < 10; i++)
{
	[instrukcje]
}

To jest przykład pominięcia inicjalizacji zmiennej i o ile zmienna "i" występuje gdzieś wcześniej i jest typu całkowitoliczbowego, taki kod zostanie zatwierdzony ✔️.

Możesz pominąć wszystkie 👇:

for (;;)
{
	[instrukcje]
}

tylko wtedy pętla jest nieskończona, więc nie radzę tak pisać 😏.

Zaznaczam ponownie, że powyższa postać jest tą pierwotną, która znajduje się w języku C, także pętla "for" występująca w innych językach programowania wcale nie musi posiadać takiej budowy 💥!

Budowa pętli "for" wytłumaczona, więc przejdę teraz do prostego przykładu praktycznego 🚀!

PRZYKŁAD UŻYCIA PĘTLI "FOR" W PROGRAMOWANIU

Prosty przykład użycia pętli "for" polegać będzie na wypisaniu wszystkich liczb całkowitych znajdujących się w tablicy wraz z samym numerem elementu, jaki obecnie jest brany pod uwagę. Skorzystam z języka C, w którym to zadanie można zrealizować w sposób następujący 👇:

#include <stdio.h>

int main(void)
{
	int numbers[] = {6, 10, -5, 14};
	int numberOfElements = sizeof(numbers) / sizeof(numbers[0]);

	for (int i = 0; i < numberOfElements; i++)
	{
		printf("Liczba %d: %d\n", i + 1, numbers[i]);
	}
	
	return 0;
}

Tłumaczę po kolei 📣.

Na początku tworzymy sobie tablicę kilku liczb całkowitych 🔢. Następnie wyznaczamy liczbę elementów ile tablica posiada. Pisząc kod w języku C można przeżyć mały "zong" bowiem nie ma w nim żadnej funkcji do pobierania aktualnej liczby elementów w tablicy i musimy sami wyznaczyć tę wartość 🙂.

Można zdefiniować sobie stałą poprzez dyrektywę "#define", lecz bardziej profesjonalnym sposobem będzie policzenie faktycznej liczby korzystając z operatora "sizeof" i wstawieniu sprytnego wyrażenia polegającego na zamianie liczby bajtów zajętych przez tę tablicę na jej rozmiar (suma liczb bajtów wszystkich elementów dzielona na liczbę bajtów pierwszego elementu ℹ️) 🔥.

Zakładając, że tablica zajmuje 4*N bajtów i wiedząc, że każdy z jej elementów zajmuje dokładnie tyle samo pamięci, powstaje bardzo prosta kalkulacja 👇:

4*N / N = 4

To jest bardzo użyteczny zapis w języku C do wyznaczania rozmiarów tablic i fajnie go znać 😉.

Została nam już tylko pętla "for". Jej zmienna iteracyjna ma przypisaną wartość 0 (zero), warunkiem wejścia jest sprawdzenie czy ta wartość jest mniejsza od liczby elementów w tablicy, a modyfikacja jest rosnąca i licznik każdorazowo rośnie o jeden 📈. To oznacza, że jej przeznaczeniem jest obsługa tablicy ✅.

Jej jedyną instrukcją jest wywołanie funkcji "printf", która przyjmuje dwie wartości całkowitoliczbowe: pierwsza jako aktualny numer elementu (zwiększamy o jeden, ponieważ wartość zmiennej iteracyjnej reprezentuje indeks ⚠️), a druga wartość elementu tablicy przy użyciu tej samej zmiennej iteracyjnej 👍. W ten sposób, program po uruchomieniu wypisze wszystkie liczby tablicy jedna po drugiej 😊.

Pętla "for" w programowaniu

Pętla "for" składa się z trzech części: inicjalizacji zmiennej iteracyjnej, warunku wejścia oraz modyfikacji zmiennej iteracyjnej. Pasuje perfekcyjnie do obsługi uporządkowanych struktur danych i wykonywania innych instrukcji z góry określoną liczbę razy.

Zanim zakończymy materiał, zwrócę Twoją uwagę na ostatni ważny wątek pętli "for", o którym warto mieć świadomość 🔔.

JAKIE WYSTĘPUJĄ POSTACIE PĘTLI "FOR" W PROGRAMOWANIU?

Ucząc się wielu języków programowania, możesz natrafić na różne postacie pętli "for" wykraczające poza jej formę podstawową 💥. Większość będzie różnić się jedynie zapisem, aczkolwiek warto znać dwie dodatkowe konstrukcje, które są dosyć często widziane 👇:

  1. zagnieżdżona pętla "for",
  2. pętla "for" przeznaczona do sekwencji (zmienna iteracyjna przyjmuje od razu element).

Zobacz jak one wyglądają 👀!

ZAGNIEŻDŻONA PĘTLA "FOR"

Pętle "for" mogą być zagnieżdżane, czyli jedna może znaleźć się w drugiej 😊! Stosuje się je w momencie, gdy tablica którą obsługujemy posiada wiele wymiarów. Zazwyczaj potrzebujemy nie więcej niż dwa, stąd też zagnieżdżona pętla "for" przyjmuje wtedy taką postać 👇:

for (int y = 0; y < numberOfRows; y++)
{
	for (int x = 0; x < numberOfColumns; x++)
	{
		[instrukcje]
	}
}

Pętla zewnętrzna służy do poruszania się po wierszach (rzędach) ↕️, a pętla wewnętrzna pozwala na poruszanie się po kolumnach ↔️. Stosujemy zagnieżdżenie, ponieważ chcemy, aby program "przeszedł" po każdej komórce takiej tablicy. Zatem, najpierw należy "wejść" do tablicy tablic oznaczającej pojedynczy rząd, a potem "wejść" do drugiego wymiaru czyli odpowiedniej komórki tego rzędu 😅.

Często będziesz potrzebować obsługi tablic wielowymiarowych, więc dobrze jest wiedzieć w jaki sposób prawidłowo wykonać zagnieżdżenie pętli "for" ⚠️!

PĘTLA "FOR" PRZEZNACZONA DO SEKWENCJI

Istnieje osobna postać pętli "for" obsługująca bezpośrednio elementy struktury danych 🔥. W takiej pętli zmienna iteracyjna przyjmuje element, a nie indeks! Jej forma wygląda nieco inaczej zależnie od języka programowania ⚠️.

W Javie określa się ją "pętlą rozszerzoną" (tu jest osobny artykuł) 👇:

for (int number : numbers) {
	[instrukcje]
}

W języku C# z kolei, rozpoznasz ją po haśle "foreach" (materiał znajdziesz tutaj) 👇:

foreach (int number in numbers)
{
	[instrukcje]
}

a w Pythonie, to jest takie samo "for", tylko tam operujemy wyłącznie na sekwencjach (kliknij tutaj, aby przejść do artykułu na ten temat) 👇:

for number in numbers:
	[instrukcje]

Każda z postaci charakteryzuje się ważnym szczegółem: operuje na jakiejś sekwencji. Może to być tablica, lista, zbiór, słownik - praktycznie wszystko, co może być "policzalne" ✅.

Ta pętla znosi konieczność pisania instrukcji odwołującej się do elementu o aktualnym indeksie "i", co może być męczące zwłaszcza, gdy tworzymy zmienną do tego celu. Dlatego warto pamiętać, że w niektórych językach programowania istnieje taka forma pętli 👍.


Koniec. Materiał wyszedł dość duży, jednak chodziło mi o zaprezentowanie tematu już w pełnej formie, ukazując wszystkie wątki jakie mogą Ci się przydać 🌟. Zrozumienie jej działania jest niezbędne, aby móc stwierdzić, że umiesz podstawy 🔥! Już teraz zapraszam do poznania kolejnej pętli: "while" 🧨!

PODOBNE ARTYKUŁY