Frage: Programm nicht verstanden...



  • piro411 schrieb:

    ich gehe dann in die main fange mit rek(4) wieder an gehe in die forschleife,

    Zwischen an und gehe passiert noch etwas wichtiges.



  • Wenn du die Werte bei der Ausgabe etwas anders gruppierst, siehst du es leichter:

    4
    3
    2
    1
    1
    22
    333
    4444
    


  • also ich bin jetzt so weit:
    das programm gibt ja 4,3,2,1 aus BEVOR es in die for schleife geht noch oder?
    dann habe ich 4,3,2,1 ausgegeben mein i is somit 1 und dann gehe ich in die for schleife.
    dort IN der For schleife---> DIE FOR SCHLEIFE GEHT NOCH VON EINER 4 aus die in die funktion übergeben wurde oder? also steht da im endeffekt int k = 0; 0<4, k++ oder?
    das heisst aber der würde dann in der for schleife zu erst ne 4 ausgeben?!

    OODER ( anderer Ansatz der for schleife)

    nach dem der 4,3,2,1 ausgegeben hat gibt der mein i=1 in die for schleife weiter also 0<1 cout <<i --> 1 wird ausgegeben
    dann im nächsten schritt wird k hochgezählt also steht da 1<1 das trifft ja nicht zu deshalb müsste er doch aus der forschleife springen und das programm muss beendet werden?!
    ich komm da einfach nicht hinter... 😕 😕



  • nach dem 2. schleifendurchlauf der for schleife wird i von 1 zu 2 umgesetzt. habe eben nen breakpoint dahin gesetzt. wie geschieht das? also wieso wird i =2 ?

    wenn mir einer das sagen könnte, also wieso nachdem 0<1 nicht mehr zutreffen kann in der for schleife-- wieso genau da i auf 2 gesetzt wird, wäre das super. denn dann weiss ich wie das ding klappt



  • piro411 schrieb:

    dann im nächsten schritt wird k hochgezählt also steht da 1<1 das trifft ja nicht zu deshalb müsste er doch aus der forschleife springen und das programm muss beendet werden?!

    Nein, die Schleife ist fertig und die Funktion wird verlassen.

    Nachdem das aber der Aufruf rek(1) war, landest du im Aufruf rek(2), und zwar direkt bei der inneren for-Schleife. Dort läuft die Schleife bis 2<2 und dann wird die Funktion beendet und kehrt zu rek(3) zurück und zwar – du ahnst es schon – zur inneren for-Schleife.



  • piro411 schrieb:

    nach dem 2. schleifendurchlauf der for schleife wird i von 1 zu 2 umgesetzt. habe eben nen breakpoint dahin gesetzt. wie geschieht das? also wieso wird i =2 ?

    Weil du von rek(1) zu rek(2) zurückspringst und da ist i=2.



  • [quote="nman"]

    piro411 schrieb:

    Nachdem das aber der Aufruf rek(1) war, landest du im Aufruf rek(2), und zwar direkt bei der inneren for-Schleife.

    wieso macht der das denn? also wieso geht der nach rek(1) wieder mit rek(2) in die for schleife bzw. wieso macht der das sozusagen rückwärts?
    also geht der einfach dei werte durch die i hatte bevor er zum 1. mal in die for schleife gegangen ist??



  • Ok ich aber wieso geht der mit rek(2) wieder in die for schleife??
    geht der einfach alle werte durch, die i hatte, bevor er zum ersten mal in die for schleife gegangen ist? also dann halt sozusagen die ausgegebenen werte (4321) nochmal durch die for schleife hoch bis zur 4 und dann erst programm ende??


  • Mod

    Rekursion scheint an dir noch vorbei zu gehen. Machen wir mal eine Nummer einfacher:

    #include <iostream>
    using namespace std;
    
    void rek(int i)
    {
    	if (i > 0)
    	{
    		cout << "Rekursionsfunktion mit i = " << i << ". Ausgabe am Anfang.\n"
    		     << "Rufe nun Funktion mit i = " << i - 1 << " auf.\n";
    		rek(i - 1);
    		cout << "Rekursionsfunktion mit i = " << i << ". Ausgabe am Ende."
    		     << " Kehre nun zurück.\n";
    	}
    }
    
    int main() 
    {
    	rek(4);
    }
    

    Verstehst du die Ausgabe dieses Programms? Erklär mal.



  • Schau dir mal mit diesem hässlichen aber etwas simpleren Programm an, wie rekursive Funktionsaufrufe ablaufen:

    #include <iostream>
    #include <string>
    
    void rek(unsigned i) {
      if (i >= 3)
        return;
    
      std::string s = "";
      for (unsigned j = 0; j<i; ++j)
        s += " | ";
    
      std::cout << s << "rek: i=" << i << " (vorher)\n";
      rek(i+1);
      std::cout << s << "rek: i=" << i << " (nachher)\n";
    }
    
    int main() {
      rek(0);
    }
    

    Ist ziemlich ähnlich wie dein ursprüngliches Programm, aber vielleicht verstehst du es durch die Ausgabe etwas besser:

    rek: i=0 (vorher)
     | rek: i=1 (vorher)
     |  | rek: i=2 (vorher)
     |  | rek: i=2 (nachher)
     | rek: i=1 (nachher)
    rek: i=0 (nachher)
    

    Setz am besten mal einen Breakpoint vor dem rek-Aufruf und geh dann mit dem Debugger Schritt für Schritt durch.

    edit: Zu langsam.



  • ACHSOOOO!!!!! ich glaub jetzt habe ich es.
    Bei der Rekursion gehe ich, sobald ich am "Ende" meiner bedingung (hier zum Beispiel i>0) angekommen bin, meine Werte wieder bis zum Anfang durch.
    Also wenn ich 4 3 2 1 habe gehe ich (Bei meinem Programm jetzt) in die Forschleife und zwar dann sozusagen rückwärts erst mit i=1 dann mit i =2 .... bis i =4, also meinen Anfangswert dann halt und gebe dann das was die Forschleife halt macht mit diesen Werten aus.
    Ich gehe nachdem die Bedingung i>0 also nicht mehr zutrifft wieder Schritt für Schritt zurück.
    Ist das soweit richtig?

    SeppJ und nman --> Eure Programme haben es verdeutlicht! Danke 😃


  • Mod

    piro411 schrieb:

    Ist das soweit richtig?

    Ich habe immer noch den Eindruck, dass du es nicht wirklich verstanden hast.

    SeppJ und nman --> Eure Programme haben es verdeutlicht! Danke 😃

    Kannst du dies immer noch erklären?

    #include <iostream>
    using namespace std;
    
    void rek(int i)
    {
        if (i > 0)
        {
            cout << "Rekursionsfunktion mit i = " << i << ". Ausgabe am Anfang.\n"
                 << "Rufe nun Funktion mit i = " << i - 1 << " auf.\n";
            rek(i - 1);
            cout << "Rekursionsfunktion mit i = " << i << ". Ausgabe in der Mitte.\n"
                 << "Rufe nun Funktion mit i = " << i - 2 << " auf.\n";
            rek(i - 2);
            cout << "Rekursionsfunktion mit i = " << i << ". Ausgabe am Ende."
                 << " Kehre nun zurück.\n";
        }
        else
        	cout << "Aufruf mit i = " << i << ", kehre sofort zurück.\n";
    }
    
    int main()
    {
        rek(3);
    }
    

    http://ideone.com/dPAnlq

    Prüf auch deine Vorstellung auch mal an ein paar größeren Zahlen als 3 beim Aufruf in der main, ob du wirklich richtig liegst.


Anmelden zum Antworten