Variable aus if-Abfrage weiter verwenden?



  • es kann natürlich sein, dass keine bedingung zutrifft. dann ist der inhalt von sol undefiniert. null (wie nulltpr) kann er jedenfalls nicht sein.



  • Vielen Dank für die schnellen Antworten. Ich habe "double" in "unsigned" geändert, erhalte damit allerdings beim Ausführen des Programms einen Wert von 134519369 für sol und danach stürzt es ab mit der Fehlermeldung "Segmentation fault (core dumped)".

    Ich habe weiterhin folgendes versucht:

    unsigned sol = 3;
       	if (rx[0] > 0.0 &&
       	    rx[0] < rx[1] &&
                rx[0] < rx[2] ) 
                 sol = 0;
    
       	else if (rx[1] > 0.0 &&
       		rx[1] < rx[0] &&
                	rx[1] < rx[2] ) 
                	sol = 1;
    
       	else if (rx[2] > 0.0 &&
       		rx[2] < rx[1] &&
              	rx[2] < rx[0] ) 
              	sol = 2;
    
       cout << "rx[0]= " << rx[0] << endl;
       cout << "rx[1]= " << rx[1] << endl;
       cout << "rx[2]= " << rx[2] << endl;
       cout << "sol= " << sol << endl;
    

    Damit erhalte ich für rx sinnvolle Werte und das Programm stürzt auch nicht ab (z.B. rx[0] = -3.14407 ; rx[1]= -1.06378 und rx[2] = 15.3603) ; die sol-Abfrage ergibt allerdings wieder 3! Wenn ich das im C++-Tutorial richtig verstanden habe, müsste der Wert von "sol" doch überschrieben werden, wenn in der Abfrage z.B. "sol = 1" gesetzt wird. Meine Abfragen habe ich auch noch einmal überprüft, ich denke nicht, dass der Fehler hier zu suchen ist, da im o.g. Beispiel 15.3603 die Bedingungen erfüllt.
    Könnte es evtl. funktionieren, dass ich meine "sol"-Variable als return-value der if-Abfrage ausgeben lassen? Habe mal ein return vor die sol = ... - Definition gesetzt, das hat das Problem leider nicht beheben können. Aber da gibt es bestimmt einen eleganten Lösungsweg für ...

    Ich danke nochmals für die schnelle Hilfe und würde mich über weitere Vorschläge sehr freuen!



  • Zeig doch mal die ganze Funktion (im Zusammenhang) und nicht nur zusammengefrickelte Zeilen.

    Das letzte

    else if
    

    sollte außerdem ein

    else
    

    sein. Falls du das so willst.

    Was ohne abschließenden else-Zweig passiert kann ich nur raten.
    Wahrscheinlich die Verwendung deiner uninitialisierten Variablen sol.



  • && bedeutet und, d.h. keine deiner Bedingungen wird erfüllt! Suchst du oder (||)?



  • if (rx[0] > 0.0 && 
               rx[0] < rx[1] && 
                rx[0] < rx[2] ) 
                 sol = 0; 
    
           else if (rx[1] > 0.0 && 
               rx[1] < rx[0] && 
                    rx[1] < rx[2] ) 
                    sol = 1; 
    
           else if (rx[2] > 0.0 && 
               rx[2] < rx[1] && 
                  rx[2] < rx[0] ) 
                  sol = 2;
    

    Was zum Teufel-?
    Und du bist dir ganz sicher, dass man das nicht eleganter mit Schleifen lösen könnte?



  • Ich nehme an rx ist ein c-Array, sollte man in c++ nicht benutzen, dafür ist der std::vector einfach zu nützlich.

    //c mit cout Lösung
    #include <iostream>
    using namespace std;
    
    int main() {
    	double rx[3];
    	unsigned sol = 0;
    
    	rx[0] = 1.1;
    	rx[1] = -6;
    	rx[2] = 1.7;
    
    	bool firstNumberFound=false;
    	for(unsigned i=0; i<3; ++i) {	//Gehe alle 3 Werte durch
    		if(rx[i] > 0.0) {			//Zahl soll Positiv sein
    			if(!firstNumberFound) {  //Ersten Index einer positiven Zahl merken
    				firstNumberFound=true;
    				sol=i;
    			}
    
    			if(rx[i] < rx[sol]) {	//Ist die Zahl kleiner als die bekannteste kleinste?
    				sol = i;			 //Index Merken
    			}
    		}
    	}
    
       cout << "rx[0]= " << rx[0] << endl;
       cout << "rx[1]= " << rx[1] << endl;
       cout << "rx[2]= " << rx[2] << endl;
       cout << "sol= " << sol << endl;
    }
    

    Dann das Ganze in c++, wenn man nur die Zahl haben möchte(die Eingangsdaten werden manipuliert durch remove_if).

    //c++ Lösung
    #include <iostream>
    #include <vector>
    #include <algorithm>
    using namespace std;
    
    bool isNegative(double i) {
    	return i<0.;
    }
    
    double findPositiveSmallest(vector<double>& Vector) {
    	vector<double>::iterator newEnd = remove_if(Vector.begin(), Vector.end(), isNegative);	//Entferne alle nicht-Positiven zahlen
    	//remove_if(Vector.begin(), Vector.end(), [](int i) {return i<0.;});	//Alternative mit Lambda, isNegativ braucht dann nicht definiert werden
    	return *min_element(Vector.begin(), newEnd);		//Gibt die kleinste Zahl zurück
    }
    
    int main() {
    	vector<double> Test;	//Ersatz für dein rx[3]
    	Test.push_back(-1.1);
    	Test.push_back(7.);
    	Test.push_back(0.1);
    
    	cout<<findPositiveSmallest(Test);
    }
    

    Den Fall, dass alle Zahlen negativ sind muss man noch hinzufügen. Hoffe, da ist nichts Falsches drin, ist schon spät, Licht aus.


  • Mod

    JaykopX schrieb:

    Dann das Ganze in c++, wenn man nur die Zahl haben möchte(die Eingangsdaten werden manipuliert durch remove_if).

    remove_if ist nicht erforderlich, man kann ja auch min_element mit einem geeigneten Komparator versehen, z.B.

    min_element(first, last, [](double a, double b){ return a > 0 ? b <= 0 || a < b : b <= 0 && a > b; });
    


  • Ich habe jetzt gesehen und sogar verstanden, was an meiner Abfrage falsch ist. Die Lösungsvorschläge funktionieren hervorragend, ich werde mir noch anlesen müssen, was genau die einzelnen Elemente daraus bedeuten und wie sie verwendet werden. Ist aber auch das erste kleine Programm, das ich ohne Anleitung versucht habe ...
    Wenn ich es fertig und funktionsfähig habe und meine Lösung in mehr als nur zwei Buchstaben von der von JaykopX vorgeschlagenen differiert, werde ich sie noch posten.

    Ganz vielen herzlichen Dank für eure Antworten!

    Viele Grüße!



  • camper schrieb:

    JaykopX schrieb:

    Dann das Ganze in c++, wenn man nur die Zahl haben möchte(die Eingangsdaten werden manipuliert durch remove_if).

    remove_if ist nicht erforderlich, man kann ja auch min_element mit einem geeigneten Komparator versehen, z.B.

    min_element(first, last, [](double a, double b){ return a > 0 ? b <= 0 || a < b : b <= 0 && a > b; });
    

    Stimmt, aber ist hier

    b <= 0 && a > b
    

    nicht überflüssig? Könnte doch so aussehen:

    min_element(first, last, [](double a, double b){ return a > 0 ? b <= 0 || a < b : false; });
    

  • Mod

    JaykopX schrieb:

    Stimmt, aber ist hier

    b <= 0 && a > b
    

    nicht überflüssig? Könnte doch so aussehen:

    min_element(first, last, [](double a, double b){ return a > 0 ? b <= 0 || a < b : false; });
    

    Dann wird nicht das am nächsten an 0 liegende Element, sondern immer das erste der Sequenz zurückgegeben, falls kein ELement postiv ist. Da der OP nicht auf diesen Fall eingegangen ist, habe ich einfach etwas genommen, was mir gerade in den SInn kam.
    Deine Version würde ich allerdings eher als

    a > 0 && ( a < b || b <= 0 )
    

    schreiben.


Anmelden zum Antworten