incomplete-type

___ tag123boost ___ Boost ist eine große Sammlung von hochwertigen Bibliotheken, die für die Verwendung in C ++ gedacht sind. Boost ist kostenlos und wird oft als "zweite Standard-Bibliothek" angesehen. ___ tag123c ___ C ++ ist eine universelle Programmiersprache. Es wurde ursprünglich als Erweiterung von C entworfen und behält eine ähnliche Syntax, ist aber jetzt eine komplett andere Sprache. Verwenden Sie dieses Tag für Fragen zu Code, der mit einem C ++ - Compiler kompiliert werden soll. ___ qstntxt ___

Betrachten Sie das folgende Code-Snippet. Der Destruktor von boost :: scoped_ptr wird am Ende der Hauptfunktion aufgerufen. Der Destruktor verwendet boost :: checked_delete, um den eingekapselten Widget-Zeiger aufzuheben.

%Vor%

Ich habe erwartet, dass dieser Code nicht kompiliert werden kann, da das Widget an der Stelle unvollständig ist, an der der Destruktor von %code% aufgerufen wird. Dies wird jedoch sauber in g ++ 4.8 und Visual Studio 2010 kompiliert. Beachten Sie die kommentierte Anweisung mit dem Ausdruck %code% in der Hauptfunktion. Wenn ich es auskommentiere, wird es nicht kompilieren, was bedeutet, dass %code% zu diesem Zeitpunkt unvollständig sein muss.

Was ist die korrekte Erklärung für dieses Verhalten?

BEARBEITEN: Einige Antworten (jetzt gelöscht) wiesen auf nicht definiertes Verhalten hin, aber ich hätte erwartet, dass die Verwendung von checked_delete in %code% destruktor einen Kompilierungsfehler verursacht. FWIW, ich benutze Boost 1.55.

    
___ tag123smartpointers ___ Ein abstrakter Datentyp, der einen Zeiger simuliert und zusätzliche Features bereitstellt, z. B. die automatische Speicherbereinigung oder die Überprüfung von Begrenzungen ___ answer24841123 ___
  

5.3.5 Löschen %code%

     

5 Wenn das Objekt gelöscht unvollständigen Klassentyp an der Stelle der Deletion und die vollständige Klasse hat, einen nicht-trivialen destructor oder eine Aufhebung der Zuordnung Funktion wird das Verhalten ist nicht definiert.

Sie würden sicherlich erwarten, dass es UB ist, denn %code% ist nicht-trivial, und Sie würden erwarten, dass die Sicherheit in Boost zu Fehler führt.

Nun, lasst uns höher graben:

  

2.2 Phasen der Übersetzung %code%

     

8 Übersetzte Übersetzungseinheiten und Instanziierungseinheiten werden wie folgt kombiniert: [Anmerkung: ...] Jede übersetzte Übersetzungseinheit wird untersucht, um eine Liste der erforderlichen Instanziierungen zu erstellen. [Hinweis: Dies kann explizit angeforderte Instanzen enthalten (14.7.2). -Hinweis] Die Definitionen der erforderlichen Vorlagen sind lokalisiert. Es ist implementationsdefiniert, ob die Quelle der Übersetzungseinheiten, die diese Definitionen enthalten, verfügbar sein muss. [Hinweis: Eine Implementierung könnte ausreichende Informationen in die übersetzte Übersetzungseinheit codieren, um sicherzustellen, dass die Quelle hier nicht benötigt wird. -Ende note] Alle erforderlichen instantiations ausgeführt Instanziierung Einheiten zu produzieren [Anmerkung:. Diese sind ähnlich wie übersetzt Übersetzungseinheiten, enthalten jedoch keine Hinweise auf instanziierten Vorlagen und ohne Vorlage Definitionen. -Hinweis] Das Programm ist fehlerhaft, wenn eine Instanziierung fehlschlägt.

Sie werden gespeichert durch Phasen der Übersetzung :
Übersetze die Übersetzungseinheit, dann instanziiere Vorlagen ...

    
___ tag123scopedptr ___ Ein von Boost bereitgestellter intelligenter Zeiger, der einen dynamisch zugewiesenen Zeiger besitzt und nicht kopiert oder verschoben werden kann, wobei der Besitz des Zeigers in seinem Bereich beibehalten wird. ___ qstnhdr ___ Wann wird ein Typ als abgeschlossen betrachtet? ___ tag123incompletype ___ In den C- und C ++ - Sprachen fehlt einem unvollständigen Typ "genügend Information, um die Größe von Objekten dieses Typs zu bestimmen." (Beispiele: Arrays mit variabler Länge, Vorwärtsdeklarationen von 'struct's und der Typ' void '.) ___
3
Antworten

Handles Vergleich: leere Klassen vs. undefinierte Klassen vs void *

Microsoft GDI + definiert viele leere Klassen, die behandelt werden sollen als handle intern. Zum Beispiel (source GdiPlusGpStubs.h ) %Vor% Es gibt zwei weitere Möglichkeiten zum Definieren von Handles. Sie sind, %Vor% Ich möchte nur...
24.12.2010, 10:47
2
Antworten

Ungültige Verwendung von unvollständigem Typ - warum kein Fehler in diesem Fall?

Ich bin verwirrt darüber, warum mein Code nicht den Fehler invalid use of incomplete type erzeugt, während all das Lesen, das ich über diesen Fehler gemacht habe, darauf hindeutet. Die Frage ergab sich aus diesem Fehler angezeigt (wie erwa...
25.09.2014, 13:56
3
Antworten

So löschen Sie alle QGraphicsItem aus QGraphicsScene

Ich habe eine abgeleitete Klasse aus QGraphicsScene geschrieben. An einem Punkt muss ich alle Elemente aus der Szene entfernen und möchte, dass die Objekte physisch zerstört werden (Destruktor wird aufgerufen). Ich habe folgendes versucht:...
15.09.2011, 12:47
1
Antwort

Zeiger auf Elementfunktion des unvollständigen Typs

Ich verstehe nicht, warum das Hinzufügen einer Forward-Deklaration für eine Klasse die Größe ihres Zeigers auf den Member-Typ ändert %Vor% Ausgabe VS2013: 4 Aber wenn ich die ersten zwei Zeilen in main () auskommentiere, dann ist die Aus...
18.06.2015, 18:43
1
Antwort

Ist es mißbräuchlich, Parameter der Elternvorlage abzuleiten, wenn der Zeiger auf die Funktion consxpr im Gültigkeitsbereich einer Klasse übergeben wird?

Minimales Beispiel, das ich bekommen habe, ist ein bisschen kompliziert: %Vor% [gcc] kompiliert den Code ohne Probleme, [clang] beschwert sich über die Übereinstimmung von Parent mit Kid problem: %Vor% Um absurder zu werden, we...
17.12.2017, 11:45
1
Antwort

Wann wird ein Typ als abgeschlossen betrachtet?

Betrachten Sie das folgende Code-Snippet. Der Destruktor von boost :: scoped_ptr wird am Ende der Hauptfunktion aufgerufen. Der Destruktor verwendet boost :: checked_delete, um den eingekapselten Widget-Zeiger aufzuheben. %Vor% Ich habe erwa...
19.07.2014, 13:47