Exceptions



  • Hi Peoples!

    Ich hab mir mal ne kleine String Klasse geschrieben (noch nicht ganz fertig) und bin dabei auf das Problem gestoßen, wie man Exceptions erstellt. Zum Beispiel hier:

    void CString::Delete(unsigned int index, unsigned int count)
    {
       unsigned int len = Length();
       if( (index >= len) || (index + count > len) )
          return;
    
       LPTSTR substr = m_String + index + count;
       LPTSTR new_pos_substr = m_String + index;
       lstrcpy(new_pos_substr, substr);
    }
    

    Hier stört mich das return; in Zeile 5. Wenn jetzt wirklich was schiefläuft, kriegt man das ja evtl. gar nicht mit. Was mache ich da jetzt am besten?





  • Danke, aber das hat mir jetzt leider gar nicht so viel gebracht. Ich weiß nämlich noch gar nicht, wie ih überhaupt Exceptions verwende. Ist in meinem Fall (s.o. im Code) überhaupt eine nötig? Und wenn ja, wie macht man das? try...catch oder throw? Ich habe echt keine Ahnung.



  • http://www.cpp-tutor.de/cpp/le16/le16_02.htm 🤡

    nimm doch std::string als vorlage und guck wie es da gemacht wird. dort wird soweit ich weiß keine exception geworfen.

    wo ist überhaupt der zusammenhang mit winapi?



  • WebFritzi schrieb:

    Hier stört mich das return; in Zeile 5. Wenn jetzt wirklich was schiefläuft, kriegt man das ja evtl. gar nicht mit. Was mache ich da jetzt am besten?

    throw "Hier ging was schief";
    


  • People1 schrieb:

    wo ist überhaupt der zusammenhang mit winapi?

    Hmm, eigentlich nur meine Klasse, in der ich LPTSTR und all die WinApi-Funktionen kapseln will. 🙄



  • Also, das hier wäre OK, ja?

    void CString::Delete(unsigned int index, unsigned int count) 
    { 
       unsigned int len = Length(); 
       if( (index >= len) || (index + count > len) ) 
          throw("CString::Delete : one of the integer parameters is too big"); 
    
       LPTSTR substr = m_String + index + count; 
       LPTSTR new_pos_substr = m_String + index; 
       lstrcpy(new_pos_substr, substr); 
    }
    


  • du kannst auch gleich std::basic_string<TCHAR> benutzen



  • Es ist schöner, wenn man eine "Klasse" wirft...

    #include <windows.h>
    #include <tchar.h>
    
    class CMyExp
    {
    public:
      CMyExp(LPCTSTR szText)
      {
        m_szText = _tcsdup(szText);
      }
      CMyExp(const CMyExp &v)
      {
        m_szText = _tcsdup(v.m_szText);
      }
      ~CMyExp()
      {
        if (m_szText != NULL)
          free(m_szText);
      }
      LPCTSTR toString()
      {
        return m_szText;
      }
    private:
      LPTSTR m_szText;
    
    };
    
    int _tmain()
    {
      try
      { 
        throw CMyExp(_T("Hello World!"));
      }
      catch(CMyExp exp)
      {
        _tprintf(exp.toString());
      }
      return 0;
    }
    


  • WebFritzi schrieb:

    Ich weiß nämlich noch gar nicht, wie ih überhaupt Exceptions verwende. Ist in meinem Fall (s.o. im Code) überhaupt eine nötig?

    Ich habe es in meiner String Klasse so gemacht, dass solche Sachen einfach nur geloggt werden. Wenn etwas gelöscht werden soll, was es gar nicht gibt, dann ist das nicht unbedingt ein Grund, weshalb eine Anwendung gleich mit Exceptions um sich werfen soll, imo. Immerhin passiert da ja nix Schlimmes. Dieser logische Fehler des Client muss sicherlich irgendwann beseitigt werden, aber bis dahin kann das Programm auf jeden Fall weiterlaufen. Ich habe für das Logging extra Funktionen/Klassen geschrieben, die die Arbeit übernehmen. Das sieht dann angewendet ungefähr wie folgt aus:

    VERIFY(offset_within_range(index, len));
    

    Hier würde halt nur geloggt werden, danach aber die Ausführung fortgesetzt werden.
    In deinem Fall wäre zB Folgendes notwendig

    VERIFY_RETURN(offset_within_range(index, len));
    

    Willst du, dass die Anwendung richtig hart bestraft wird, kann man auch Folgendes machen

    VERIFY_ERROR(offset_within_range(index, len));
    

    Hier fliegt dann halt eine Exception oder die Anwendung wird hart beendet.

    Wie auch immer, alles was intern passiert, bleibt transparent. Der Anwender muss sich darum also nicht kümmern. So kann man später die Fehlerbehandlung auch ändern, ohne dass man grossen Aufwand betreiben muss. Von der Benutzung her sind das also alles spezifische Asserts.


Anmelden zum Antworten