Ich verstehe nicht, was hier falsch ist (Vectoren, while-Schleifen, usw.)....



  • Hallo,

    das ist mein Code mit dem ich versuche eine .obj Datei auszulesen:

    class VERTICES {
    public:
    	float x;
    	float y;
    	float z;
    };
    void obj_laden()
    {
    	std::ifstream Datei;
    	Datei.open("C:\bla.obj", std::ios::in);
    
    	std::string Line;
    	std::vector<VERTICES> Vectoren;
    	while(std::getline(Datei, Line))
    	{
    		const std::string s = Zeilen(Line, 0);
    
    		if(s == "v")
    		{
    			VERTICES Vector;
    			Vector.x = NachFloat(Zeilen(Line, 1));
    			Vector.y = NachFloat(Zeilen(Line, 2));
    			Vector.z = NachFloat(Zeilen(Line, 3));
    
    			Vectoren.push_back(Vector);
    		}
                    // erst einmal nur die "v" 
    
    	}
    	Datei.clear();
    }
    

    aufrufen tue ich die Messagebox so:

    std::stringstream sstr;
    	sstr << Vectoren[0].z;
    	std::string str1 = sstr.str();
    	if(Vectoren.size() == 0)
    	{
    	MessageBox(HWND_DESKTOP , str1.c_str(), "Test", MB_OK | MB_ICONWARNING | MB_TASKMODAL);
    	}
    

    Wenn ich mit meiner Messagebox überprüfen will, ob das die Vectoren gefüllt worden sind. Leider sind sie das nicht.

    Danke schon mal für eure Hilfe!



  • liegt wohl an der indirekten nicht vorhandenheit eines zusammenhangs



  • Was meinst du damit?



  • Wenn du den Ablauf oder den Wert von Variablen überprüfen willst, machst du das am besten nicht mit einer MessageBox, sondern mit dem Debugger! Setze dir Breakpoints an strategisch wertvollen Stellen (im Visual Studio mit F9), gehe schrittweise durch den Code (im VS mit F10, F11), überprüfe dabei Variableninhalte (im VS z.B. mit dem Überwachungsfenster, oder auch einfach per Tooltip, indem du mit der Maus auf den jeweiligen Bezeichner gehst).

    Wenn dein vector nicht gefüllt ist, wird die Bedingung dafür wohl einfach nicht wahr werden...

    Merke: der Debugger ist das Werkzeug der Wahl zum debuggen! 💡

    Übrigens solltest du überprüfen, ob die Datei auch wirklich geöffnet werden konnte...



  • if(Vectoren.size() == 0)
    

    Zeige die MessageBox wenn keine Elemente in Vectoren sind.

    Besser:

    if(Vectoren.size() != 0)
    


  • Wie kommt der vector aus der Funktion obj_laden raus?



  • Wie meinst du "raus"?



  • Toyota schrieb:

    Wie meinst du "raus"?

    Du legst den vector lokal in der Funktion an. Mit dem Ende der Funktion hört er auf zu existieren.



  • der vector hat nur einen lokalen gültigkeitsbereich.
    er existiert nur in deiner funktion und wird gelöscht, sobald das ende der funktion erreicht ist.

    du musst irgendwie dafür sorgen, dass der vektor nach außen hin übergeben wird.
    das kannst du zum beispiel durch ein return der variable am ende deiner funktion erreichen.
    dann musst du aber noch die signatur deiner funktion (genauer gesagt den rückgabewert der funktion) entsprechend anpassen.

    jperl



  • ok Danke! Jetzt wollte ich aber noch etwas ausprobieren: statt am Ende der Funktion mit return den Vector weiterzugeben, wollte ich nach Datei.clear(); die Messagebox aufrufen. Ich bekomme aber die Fehlermeldung von vector.h, was bedeutet das mein Vector nicht gefüllt ist. Das müsste er aber sein, weil die Messagebox in der Funktion ja noch drinnen ist. Der Code sieht so aus:

    void obj_laden()
    {
        std::ifstream Datei;
        Datei.open("C:\bla.obj", std::ios::in);
    
        std::string Line;
        std::vector<VERTICES> Vectoren;
        while(std::getline(Datei, Line))
        {
            const std::string s = Zeilen(Line, 0);
    
            if(s == "v")
            {
                VERTICES Vector;
                Vector.x = NachFloat(Zeilen(Line, 1));
                Vector.y = NachFloat(Zeilen(Line, 2));
                Vector.z = NachFloat(Zeilen(Line, 3));
    
                Vectoren.push_back(Vector);
            }
                    // erst einmal nur die "v"
    
        }
        Datei.clear();
        std::stringstream sstr;
        sstr << Vectoren[0].z; // das will er nicht
        std::string str1 = sstr.str();
        if(Vectoren.size() == 0)
        {
        MessageBox(HWND_DESKTOP , str1.c_str(), "Test", MB_OK | MB_ICONWARNING | MB_TASKMODAL);
        }
    }
    


  • bist du dir sicher, dass die bedingung in der schleife überhaupt erfüllt wird und etwas im vector stehen muss?

    jperl



  • Normalerweise schon. Vorher hatte ich in der Schleife Datei.eof(): gleicher Effekt. Die .obj Datei ist vorhanden und besteht ganz normal aus "v", "vt" und "f".



  • toyota schrieb:

    Normalerweise schon. Vorher hatte ich in der Schleife Datei.eof(): gleicher Effekt. Die .obj Datei ist vorhanden und besteht ganz normal aus "v", "vt" und "f".

    naja normalerweise ist so eine sache.
    du sollt sicher sein, dass er überhaupt was hineinspeichert.
    gibt dir am besten etwas aus, wenn er in der if-abfrage drin ist, dann kannst du sicher sein, dass es nicht daran liegt.

    jperl



  • ok jetzt habe ich mit

    if(!Datei.good())
        {
        Datei.close();
    	MessageBox(HWND_DESKTOP , "Datei konnte nicht geöffnet werden.", "Fehler", MB_OK | MB_ICONWARNING | MB_TASKMODAL);
        }
    

    überprüft ob die Datei überhaupt gefunden wird. Das wird sie aber nicht, was ich komisch finde. Der Pfad ist immer noch "C:\2.obj" und in meinem Lokalen Datenträger C: ist diese Datei vorhanden.



  • probiers mal mit dem pfad C:\\bla.obj.
    du musst das \ escapen.

    jperl



  • toyota schrieb:

    /* ... */
    Datei.open("C:\bla.obj", std::ios::in);
    /* ... */
    

    Probier mal:

    Datei.open("C:\\bla.obj", std::ios::in);
    

    oder noch besser (wegen Plattformunabhängigkeit):

    Datei.open("C:/bla.obj", std::ios::in);
    


  • Unabhängig vom Backslash escapen: ich sagte ja schon mal, wenn du dir nicht sicher bist, ob dein Ablauf stimmt und welchen Wert deine Variablen zu einer bestimmten Zeit haben, dann nutze die Möglichkeiten des Debuggers! Das machen Anfänger oft viel zu selten (oder gar nicht). Wenn du wissen willst, ob die Bedingung für's push_back überhaupt erfüllt ist und er in diesen Zweig 'reingeht, dann setze dort einen Breakpoint und sieh nach. So hast du absolute Gewissheit. Das ist deutlich besser als Vermutungen wie 'normalerweise schon'. 🙂

    P.S.: Hier gibt's auch einen Artikel zum Debuggen. Der bezieht sich zwar auf das veraltete VS6, aber man lernt in jedem Fall als Anfänger eine Menge.
    http://magazin.c-plusplus.net/artikel/Debuggen mit VCPlusPlus6



  • Vielen Dank an alle 👍
    Jetzt hat alles geklappt


Anmelden zum Antworten