Pętla for

0

Na zajęciach dostaliśmy taki przykład do przeanalizowania, co będzie wynikiem działania pętli:

    int a=1,b=2,c=3;
    
    for(printf("%d", a++); printf("%d%d",printf("%d",b),c*10)-2; c+a)
    {
        c==--a;
        c=c-printf("0");
    }

Czy ktoś jest w stanie wyjaśnić mi to krok po kroku? Normalne pętle umiem, wszystkie praktycznie, pisze proste programy, ale z takim czymś się nigdzie nie spotkałem.

2

Dość nieżyciowy kod. printf zwraca liczbę wypisanych znaków.

for(init; condition; expr)

W pierwszym wyrażeniu pętli masz printf("%d", a++), sprawa dość prosta (inkrementujesz a, wypisujesz 1)

  1. Potem warunek printf("%d%d",printf("%d",b),c*10)-2. Ponieważ b nigdzie nie modyfikujesz, wypisane będzie 21X, gdzie X to c*10, 2 to b, a 1 to wynik wewnętrznego printfa (który wykona się pierw, wobec czego pierw wypisze 2)
  2. c==--a; dekrementujesz a, c nie zmieniasz bo to porównanie
  3. c=c-printf("0"); odejmujesz 1 (ilość znaków wypisanych - 0 to jeden znak) od c
  4. c+a dodawanie bez side-effectów, nic się nie dzieje.
    Tak więc wypisane zostaje:

1 z kroku bez numerka
2130 - pkt 1 (c = 3)
0 - pkt 3 (c ⟵ 2)
2120 - pkt 1 (c = 2)
0 - pkt 3 (c ⟵ 1)
2110 - pkt 1 (c = 1)
0 - pkt 3 (c ⟵ 0)
210 - pkt 1 (c = 0). W tym momencie zewnętrzny printfwarunku zwraca2, więc po odjęciu 2zostaje0` i warunek nie zostaje spełniony.

0
  1. Funkcja printf() w C++ zwraca liczbę wypisanych znaków (chyba).
  2. Operator "," wykonuje to, co po lewej stronie, a potem prawej i zwraca, to co po prawej. // tutaj nie występuje.
  3. W C++ wszystko co nie jest zerem, jest prawdą.

A najlepiej odpal sobie ten program, ewentualnie podziel na małe części i zobacz, co zwracają.

1

I słusznie, bo to kod-potwór. Aż się boję zapisywać i przepuszczać przez debugger, bo mi jeszcze kota zje… Więc zanalizuję ręcznie:

Zaczynamy, a = 1, b = 2, c = 3.
Inicjalizacja pętli: wyświetla 1 (wartość a), po czym inkrementuje a. Teraz (a = 2, b = 2, c = 3).
Następnie testowany jest warunek zakończenia pętli. Zewnętrzny printf nam wyświetli dwie liczby, pierwszą z nich będzie wartość zwracana przez wewnętrznego printfa — czyli liczba wypisanych znaków (lub kod błędu, jeśli się nie uda). Wewnętrzny printf wyświetla wartość zmiennej b — czyli 2, potem zewnętrzny wyświetli liczbę znaków w zapisie 2 — tzn. 1 — i zaraz po tym c * 10, czyli 30. Czyli wyświetlone zostanie na tym etapie, podsumujmy, 2130. Zewnętrzny printf wydrukował więc trzy znaki, trzy minus dwa to jeden, pętla leci dalej.
Dalej wykonuje się ciało pętli: a jest zmniejszane o jeden, po czym c jest ustawiane na to a, tak więc teraz (a = 1, b = 2, c = 1). Druga linia przypisuje do c wartość c - 1 (vide supra), tak więc mamy (a = 1, b = 2, c = 0).
Później mamy instrukcję po pętli, sumuje ca i nie robi z tym nic; to tylko taka „zaciemniajka”.
I znowu warunek pętli: wewnętrzny printf daje 2, po czym zewnętrzny 10, łącznie dwa znaki, dwa minus dwa to zero, koniec męki, idę się napić.

1 użytkowników online, w tym zalogowanych: 0, gości: 1