tutorials.de Buch-Aktion 05/2012
Like Tree1Danke
  • 1 Beitrag von deepthroat
ERLEDIGT
NEIN
ANTWORTEN
5
ZUGRIFFE
407
EMPFEHLEN
  • An Twitter übertragen
  • An Facebook übertragen
AUF DIESES THEMA
ANTWORTEN
  1. #1
    Onkel Schuppig Onkel Schuppig ist offline Mitglied Gold
    Registriert seit
    Apr 2005
    Beiträge
    191
    Hallo zusammen,
    der unten gezeigte Code-Schnipsel reagiert merkwürdig. Ich möchte möglichst am Stück Speicher reservieren. Wenn das nicht möglich ist, dann die Hälfte.
    Wenn das auch nicht möglich ist, dann ein Viertel, usw. Beim Test mit zu großem n springt die Routine auch wie beabsichtigt in den catch-Block. Aber danach geht es nicht etwa im try-Block weiter, sondern es wird eine weitere Ausnahme geworfen namens "privileged instruction". Was stimmt denn da nicht?
    Info: facemap ist eine std::map und freefaces ein std::vector.

    Code :
    1
    2
    3
    4
    5
    6
    7
    8
    9
    
    FaceMap::size_type n(facemap.size());
    while (true) {  
       try {
         freefaces.reserve(n);
         break;
       } catch (bad_alloc) {
         n /= 2;
       }
     }
     
    Grüße OS

  2. #2
    deepthroat deepthroat ist offline Mitglied Diamant
    tutorials.de Premium-User
    Registriert seit
    Jun 2005
    Beiträge
    8.168
    Hi.

    Die std::vector resize() Methode deiner verwendeten STL Implementierung scheint nicht exception-safe zu sein.

    Versuch's mal so:
    Code cpp:
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    
    FaceMap::size_type n(facemap.size());
    while (true) {  
       try {
         std::vector v(n);
         freefaces.swap(v);
         break;
       } catch (bad_alloc) {
         n /= 2;
       }
     }
    Welchen Compiler verwendest du denn? Ist das Verhalten mit einem Minimalbeispiel nachvollziehbar?

    Gruß

    PS: Du solltest übrigens grundlegend Ausnahmen immer by-reference fangen, nicht unbedingt by-value.
    Geändert von deepthroat (01.03.10 um 11:48 Uhr)
     
    If at first you don't succeed, try again. Then quit. No use being a damn fool about it.

  3. #3
    Onkel Schuppig Onkel Schuppig ist offline Mitglied Gold
    Registriert seit
    Apr 2005
    Beiträge
    191
    Mein Rechner geht z.B. bei folgenden Beispiel in die Knie. Ich habe 2 GB RAM, Win XP 32, Visual C++ 2005 Prof.
    Code :
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    
    struct test {
      double v[1000];  // Hauptsache verschwenderisch
    };
    vector<test> vec;
     
    size_t n = 1000000;
    while (true) {  
      try {
        vec.reserve(n);
        break;
      } catch (const bad_alloc&) {
        n /= 2;
      }
    }
     
    Grüße OS

  4. #4
    Onkel Schuppig Onkel Schuppig ist offline Mitglied Gold
    Registriert seit
    Apr 2005
    Beiträge
    191
    Hmm, wenn ich catch(...) verwende, scheint es zu klappen.
    Code cpp:
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    
    struct test {
      double v[1000];  // Hauptsache verschwenderisch
    };
    vector<test> vec;
     
    size_t n = 1000000;
    while (true) {  
      try {
        vec.reserve(n);
        break;
      } catch (...) {
        n /= 2;
      }
    }
     
    Grüße OS

  5. #5
    deepthroat deepthroat ist offline Mitglied Diamant
    tutorials.de Premium-User
    Registriert seit
    Jun 2005
    Beiträge
    8.168
    Hi.

    Das liegt aber dann nicht an einer "privileged instruction" Ausnahme, sondern einfach daran, das du versucht hast mehr als die maximale Anzahl von Elementen des Vektors zu reservieren (std::length_error).

    Code cpp:
    1
    
    vec.reserve(std::min(n, vec.max_size()));
    Gruß
    Onkel Schuppig bedankt sich. 
    If at first you don't succeed, try again. Then quit. No use being a damn fool about it.

  6. #6
    Onkel Schuppig Onkel Schuppig ist offline Mitglied Gold
    Registriert seit
    Apr 2005
    Beiträge
    191
    Code cpp:
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    
    #include <vector>
    using namespace std;
     
    struct test {
      double v[1000];  // Hauptsache verschwenderisch
    };
    vector<test> vec;
     
    size_t n = 1000000;
    while ( true )  {
      try {
        vec.reserve( min( n, vec.max_size() ) );
        break;
      } catch ( const bad_alloc& )  {
        n /= 2;
      }
    }
    Mit dieser Variante bin ich nun zufrieden.
    length_error() kann gar nicht erst auftreten und andere Ausnahmen als bad_alloc werden nicht behandelt. Schließlich sind nicht alle erdenklichen Ausnahmen durch n /= 2 zu lösen.
    Vielen Dank!
     
    Grüße OS

Ähnliche Themen

  1. Antworten: 17
    Letzter Beitrag: 18.05.09, 15:00
  2. GDI+ Exception bei PicBox.Image.Save - warum?
    Von Asterix-Ac im Forum .NET Archiv
    Antworten: 3
    Letzter Beitrag: 08.11.07, 15:32
  3. JBoss mit MySql, boolean-Spalte wirft Exception
    Von turbowiesel im Forum Enterprise Java (JEE, J2EE, Spring & Co.)
    Antworten: 0
    Letzter Beitrag: 27.12.06, 22:12
  4. ListBox wirft Exception (schwer)
    Von Rippa_HD im Forum .NET Archiv
    Antworten: 1
    Letzter Beitrag: 08.05.04, 11:31
  5. An unhandled exception - Doch warum
    Von Konstantin Gross im Forum .NET Archiv
    Antworten: 7
    Letzter Beitrag: 09.03.04, 22:03

Stichworte