CString:Format()



  • Hallo,

    wie kann ich einen CString mittels Format() einem anderen CString hinzufügen?

    CString test ("teststring"); 
    CString str ("here is the %%s"); 
    CString end; 
    
    //bringt leider eine fehlermeldung in output.c 
    end.Format(str, test); 
    
    //das funktioniert
    end.Format(str, _T("test"));
    

    Gruß
    Johannes



  • test.GetBuffer() sollte klappen.

    EDIT: Also so:

    end.Format(str, test.GetBuffer());
    


  • _matze schrieb:

    test.GetBuffer() sollte klappen.
    EDIT: Also so:

    end.Format(str, test.GetBuffer());
    

    geht leider auch nicht, bekomm ich auch den gleichen Fehler in der output.c Datei angezeigt.



  • Ach, das zweite '%' ist ja zuviel. So geht's:

    CString test ("teststring");
        CString str ("here is the %s");
        CString end;
    
        end.Format(str, test);
    

    Eine Fehlermeldung habe ich übrigens auch mit deinem Code nicht bekommen. Wenn du uns sagst, wie die lautet (falls sie noch mal auftritt), kann man auch eher was dazu sagen.

    EDIT:
    Kurze Erklärung: %s ist ja keine Escapesequenz, man muss also nicht 'doppeln' wie beim Backslash. Das ist lediglich ein Platzhalter für Formatstrings von Funktionen wie printf, scanf oder auch CString::Format. Wenn du in einem solchen Formatstring "%s" unterbringen willst, ohne dass ein String eingesetzt werden soll, notierst du "%%s", da "%%" => '%'. Aber bei Stringliteralen im Code kannst du ganz normal "%s" schreiben.



  • hab grad etwas nachgeforscht und mit diesem einfachen Beispiel funktioniert es, in meinem Code, hab ich allerdings zuvor einen Funktionsaufruf dabei GetResource() und nach diesem Aufruf geht CString.Format() nicht mehr.

    BOOL GetResource(const int& idrHTML, CString& rString); 
    
    CString test;
    CString teststr ("test");  
    CString str; 
    
    if(GetResource(id, test)
    {
       str.Format(test, teststr); 
    
    }
    

    Fehlermeldung: "incorrect format specifier, 0"



  • Johannes K. schrieb:

    hab grad etwas nachgeforscht und mit diesem einfachen Beispiel funktioniert es, in meinem Code, hab ich allerdings zuvor einen Funktionsaufruf dabei GetResource() und nach diesem Aufruf geht CString.Format() nicht mehr.

    BOOL GetResource(const int& idrHTML, CString& rString); 
    
    CString test;
    CString teststr ("test");  
    CString str; 
    
    if(GetResource(id, test)
    {
       str.Format(test, teststr); 
    
    }
    

    Fehlermeldung: "incorrect format specifier, 0"

    Du hast test bislang nicht initialisiert. Ich vermute mal, dass bei einem leeren CString und einer (impliziten) Konvertierung nach char* einfach 0 rauskommt, daher die Fehlermeldung. Weise test deinen String aus dem Beispiel zu (da war es noch str), dann sollte es klappen.

    EDIT: Hab gerade ignoriert, dass GetResource vermutlich test füllen soll, ja? Tut es das denn? Setze dort bitte mal einen Haltepunkt und sieh dir an, was beim Aufruf von str.Format tatsächlich in test steht

    EDIT2: Herrje, die Funktion dort heißt ja auch GetResource! 😃 Und du führst innerhalb dieser ohne Bedingung wieder GetResource aus. Das dürfte eine schöne Endlosrekursion sein...



  • _matze schrieb:

    Du hast test bislang nicht initialisiert. Ich vermute mal, dass bei einem leeren CString und einer (impliziten) Konvertierung nach char* einfach 0 rauskommt, daher die Fehlermeldung. Weise test deinen String aus dem Beispiel zu (da war es noch str), dann sollte es klappen.

    test wird in GetResource() mit einem CString belegt im UTF-8 Format. Also leer ist der String auf keinen Fall.



  • Hier mal die GerResource(). scheint ja, dass hier anscheinend etwas nicht stimmt im Bezug auf CString.Format().

    static bool GetResource(const int& idrHTML, CString& rString)
    {
    bool retVal = false;
    	try
    	{		
    		HRSRC hSrc = FindResource(NULL, MAKEINTRESOURCE(idrHTML), RT_HTML);
    		if (hSrc != NULL)
    		{
    			HGLOBAL hHeader = LoadResource(NULL, hSrc);
    			if (hHeader != NULL)
    			{
    				LPSTR lpcHtml = static_cast<LPSTR>(LockResource(hHeader));
    				if (lpcHtml != NULL)
    				{
    					rString = CString(lpcHtml);
    					retVal = true;
    				}
    				UnlockResource(hHeader);
    			}
    			FreeResource(hHeader);
    		}
    	}
    	catch (CMemoryException* e)
    	{
    		SetLastError(ERROR_FUNCTION_FAILED);
    		e->ReportError();
    		e->Delete();
    		retVal = false;
    	}
    
    }
    


  • Johannes K. schrieb:

    _matze schrieb:

    Du hast test bislang nicht initialisiert. Ich vermute mal, dass bei einem leeren CString und einer (impliziten) Konvertierung nach char* einfach 0 rauskommt, daher die Fehlermeldung. Weise test deinen String aus dem Beispiel zu (da war es noch str), dann sollte es klappen.

    test wird in GetResource() mit einem CString belegt im UTF-8 Format. Also leer ist der String auf keinen Fall.

    Siehe meine EDITs...

    Du rufst hier GetResource auf. Dann rufst du darin GetResource auf. Dann rufst du... endlose Rekursion. Du musst schon irgendeine Abbruchbedingung definieren.

    EDIT: Ach sorry, hab nicht richtig hingesehen. Das war nur ein Prototyp dort oben... 🙄



  • _matze schrieb:

    EDIT2: Herrje, die Funktion dort heißt ja auch GetResource! 😃 Und du führst innerhalb dieser ohne Bedingung wieder GetResource aus. Das dürfte eine schöne Endlosrekursion sein...

    Den Satz verstehe ich jetzt leider nicht. Ich führe einmal die Funktion GetResource() aus, danach ist der Cstring gefüllt und anschließend rufe ich einmal CString.Format() auf bzw. ich möchte es gern aufrufen..

    Wo hab ich hier jetzt eine Endlosrekursion?



  • Johannes K. schrieb:

    _matze schrieb:

    EDIT2: Herrje, die Funktion dort heißt ja auch GetResource! 😃 Und du führst innerhalb dieser ohne Bedingung wieder GetResource aus. Das dürfte eine schöne Endlosrekursion sein...

    Den Satz verstehe ich jetzt leider nicht. Ich führe einmal die Funktion GetResource() aus, danach ist der Cstring gefüllt und anschließend rufe ich einmal CString.Format() auf bzw. ich möchte es gern aufrufen..

    Wo hab ich hier jetzt eine Endlosrekursion?

    Wie gesagt, ich habe mich da verlesen. Ich dachte, du hättest eine Funktion GetResource gepostet, dabei stand bei dir oben nur der Prototyp der Funktion (geschweifte Klammer statt Semikolon gelesen). 🙂



  • Also ich kann das Fehlverhalten nicht nachvollziehen. Ich habe mir gerade schnell eine Mini-MFC-Anwendung erstellt und deine Funktion ausgeführt (leicht abgeändert, mit RT_DIALOG). Und egal, wie ich es drehe, ich bekomme keinen Fehler.

    EDIT: Du solltest versuchen, dem Fehler selbst auf die Schliche zu kommen. Und zwar, in dem du deinen Code soweit reduzierst, dass mit minimaler Größe dein Fehler noch auftritt. Dann ist er quasi isoliert und du kannst per Debugger vermutlich ganz schnell sehen, wo genau der Fehler ist.



  • _matze schrieb:

    Also ich kann das Fehlverhalten nicht nachvollziehen. Ich habe mir gerade schnell eine Mini-MFC-Anwendung erstellt und deine Funktion ausgeführt (leicht abgeändert, mit RT_DIALOG). Und egal, wie ich es drehe, ich bekomme keinen Fehler.

    Es ist auch seltsam, dass z.B. CString.FormatMessage() einwandfrei funktioniert aber CString.Format() ebend nicht...



  • Ein Problem ist auch, dass ich nicht sicher sein kann, dass dein geposteter Code wirklich dem von dir verwendeten gleich ist. Du hast nun schon zweifach fehlerhaften Code gepostet (Klammer fehlte, return-Statement fehlte). Dein Code, sinnvoll von Fehlern befreit, läuft in meiner Testanwendung problemlos. Ich weiß nicht, was ich dazu noch sagen soll. Befolge meine Ratschläge (letzter Post, EDIT) und versuche so, dem Fehler auf die Schliche zu kommen. Merke: der Debugger ist dein Freund!



  • ich glaube es liegt am Format von test-String

    if(GetResource(id, test)
    {
    
      LPTSTR lpszData = new TCHAR[test.GetLength()+1];
    
    }
    

    Der CString test beinhaltet genau den UTF-8 Code den ich als Resource auch abgespeichert habe.

    lpszData beinhaltet nur noch eckige Kästchen - daher vielleicht auch die Fehlermeldung "incorrect format specifier". Aber wie muss ich es abändern, dass es funktionieren kann?



  • Johannes K. schrieb:

    ich glaube es liegt am Format von test-String

    if(GetResource(id, test)
    {
    
      LPTSTR lpszData = new TCHAR[test.GetLength()+1];
    
    }
    

    Der CString test beinhaltet genau den UTF-8 Code den ich als Resource auch abgespeichert habe.

    lpszData beinhaltet nur noch eckige Kästchen - daher vielleicht auch die Fehlermeldung "incorrect format specifier". Aber wie muss ich es abändern, dass es funktionieren kann?

    Du initialisierst lpzData ja auch nicht in dem Beispiel (du allozierst lediglich Speicher, beschreibst diesen dann aber nicht), das ist so also nicht aussagekräftig...


Anmelden zum Antworten