Kleine Taxonomie für Typen (fundamental, POD, UDT, ...)



  • Da es hierzu öfter Fragen gibt (was ist ein POD? was ist ein UDT? etc.) habe ich mal eine kleine Übersicht gemacht, die vielleicht als nützlich angesehen wird.
    Kritik und Ergänzungsvorschläge sind willkommen.

    - bedeutet, dass genau ein Punkt der Aufzählung ist für den jeweiligen Typ zutreffend ist
    x bedeutet, dass alle Punkte der Aufzählung für den jeweiligen Typen zutreffen

    Alle Typen

    - Fundamentale Typen (fundamental types)

    - arithmetische Typen (arithmetic types)

    - integrale Typen (integral types)

    - vorzeichenbehaftete integrale Typen (signed integral types)

    - signed char
    - short
    - int
    - long
    - (long long)

    - vorzeichenlose integrale Typen (unsigned integral types)

    - unsigned char
    - unsigned short
    - unsigned
    - unsigned long
    - (unsigned long long)

    - andere

    - char: verhält sich implementationsabhängig entweder wie signed char oder unsigned char
    - wchar_t: verhält sich implementationsabhängig wie ein bestimmter vorzeichenloser oder vorzeichenbehafteter integraler Typ
    - bool: ist vorzeichenlos, gehört aber nicht zu dieser Kategorie und braucht ein paar Sonderregeln

    - Gleitkommatypen (floating point types)

    - float
    - double
    - long double

    - void

    - Zusammengesetzte Typen (compound types)

    - Arrays (arrays)
    - Funktionen (functions)
    - Zeiger auf Objekte oder Funktionen oder void (pointer)
    - Referenzen auf Objekte oder Funktionen (references)
    - Klassen (classes)

    - union
    - Strukturen (structs)

    - struct
    - class

    - Aufzählungen (enumerations)
    - Zeiger auf nicht-statische Member (pointer to (non-static) member): das "nicht-statisch" lässt man für gewöhnlich weg

    Objekttypen (object types)

    - alle außer void, Referenzen, Funktionen

    Skalare Typen (scalar types): alle Objekttypen, die keine Komponenten haben

    - arithmetische Typen
    - Zeiger
    - Zeiger auf Member
    - Aufzählungen

    Aggregate (aggregates)

    - Arrays
    - Klassen

    x ohne vom Nutzer deklarierte Konstruktoren
    x ohne nicht-statische protected oder private Datenmember
    x ohne Basisklassen
    x ohne virtuelle Funktionen

    POD (plain old data) - rekursive Definition:

    - Skalare Typen
    - POD-Klasse

    x Klassen-Aggregat
    x ohne vom Nutzer deklarierten Destruktor
    x ohne vom Nutzer deklarierten Zuweisungsoperator
    x ohne nichtstatische nicht-POD-Datenmember

    - union: POD-union
    - Struktur: POD-struct

    - Arrays aus PODs

    PODs sind layoutkompatibel zu ihrem Äquivalent in C (sofern es eins gibt). Ihre Lebenszeit entspricht der Dauer der Reservierung von Speicher für diesen Typ,
    der Ausführung eines Konstruktors oder Destruktors bedarf es nicht. zudem dürfen sie mit Funktionen wie etwa memcpy modifiziert werden.

    UDT (user defined types)

    - Klassen
    - Aufzählungen

    "eingebaute Typen" (build-in types): informell

    - Typen, die keine UDTs sind

    Jeder Typ außer Referenzen kann als Typ eines Ausdrucks auftreten.

    Typen können vollständig oder unvollständig sein.
    Ein Typ ist unvollständig, wenn es sich um void oder um eine Klasse handelt, die deklariert und noch nicht definiert wurde.
    Zudem sind Arraytypen unvollständig, solange ihr Elementtyp unvollständig ist, oder ihre Dimension unspezifiziert ist.
    Sonst ist der Typ vollständig.
    Ein unvollständiger Typ genügt in der Regel in einer Deklaration, die keine Definition ist. Wichtigste Ausnahme davon ist die Deklaration von
    nicht-statischen Datenmembern.

    Alle Typen außer Referenzen, Funktionen und Arrays können mit const oder volatile qualifiziert sein. Das ändert nicht ihre Klassifikation in obigem Schema, aber sie
    sind verschieden von dem entsprechenden Typ mit anderer cv-Qualifikation. Ein cv-qualifizierter Typ ist vollständig, wenn die
    unqualifizierte Version vollständig ist.


  • Mod

    camper hat in einem anderen Thread die Auflistung für die neuen Begriffe und Änderungen in C++11 aktualisiert:

    camper schrieb:

    - bedeutet, dass genau ein Punkt der Aufzählung ist für den jeweiligen Typ zutreffend ist
    x bedeutet, dass alle Punkte der Aufzählung für den jeweiligen Typen zutreffen
    
    Alle Typen
    
        - Fundamentale Typen (fundamental types 3.9.1)
            - arithmetische Typen (arithmetic types 3.9.1/8)
                - integrale Typen (integral types / integer types 3.9.1/7)
                    - vorzeichenbehaftete integrale Typen (signed integer types 3.9.1/2)
                        - vorzeichenbehaftet integrale Standardtypen (standard signed integer types 3.9.1/2)
                            - signed char
                            - short
                            - int
                            - long
                            - long long
                        - erweiterte vorzeichenbehaftete Integer (extended signed integer types 3.9.1/2) - optional (implementation-defined)
                    - vorzeichenlose integrale Typen (unsigned integral types 3.9.1/3)
                        - vorzeichenlose integrale Standardtypen (standard unsigned integer types 3.9.1/3)
                            - unsigned char
                            - unsigned short
                            - unsigned
                            - unsigned long
                            - unsigned long long
                        - erweiterte vorzeichenbehaftete Integer (extended unsigned integer types 3.9.1/3) - optional (implementation-defined)
                    - andere
                        - bool: ist vorzeichenlos, gehört aber nicht zu dieser Kategorie und braucht ein paar Sonderregeln (3.9.1/6)
                        - char: verhält sich implementationsabhängig entweder wie signed char oder unsigned char (3.9.1/1)
                        - wchar_t: verhält sich implementationsabhängig wie ein bestimmter vorzeichenloser oder vorzeichenbehafteter integraler Typ (3.9.1/5)
                        - char16_t: eigenständiger Typ, äquivalent zu std::uint_least16_t (3.9.1/5)
                        - char32_t: eigenständiger Typ, äquivalent zu std::uint_least32_t (3.9.1/5)
                - Gleitkommatypen (floating point types 3.9.1/8)
                    - float
                    - double
                    - long double
            - void (3.9.1/9)
            - std::nullptr_t (3.9.1/10)
        - Zusammengesetzte Typen (compound types 3.9.2)
            - Arrays (arrays)
            - Funktionen (functions)
            - Zeiger (pointer)
                - Objektzeiger (object pointer types 3.9.2/3)
                    - Zeiger auf Objekte (pointer to object types)
                    - Zeiger auf void (pointer to void)
                - Funktionszeiger (function pointer types 3.9.2/3)
            - Referenzen auf Objekte oder Funktionen (references)
                - lvalue-Referenzen (lvalue references)
                - rvalue-Referenzen (rvalue references)
            - Klassen (classes)
                - union
                - Strukturen (structs)
                    - struct
                    - class
            - Aufzählungen (enumerations) (s.u.)
            - Zeiger auf nicht-statische Member (pointer to (non-static) member)
    
    Zeichentypen (character types)
        - char
        - signed char
        - unsigned char
    
    Objekttypen (object types 3.9/8)
    
        - alle außer void, Referenzen, Funktionen
    
    Skalare Typen (scalar types): alle Objekttypen, die keine Komponenten haben
    
        - arithmetische Typen
        - Zeiger
        - Zeiger auf Member
        - Aufzählungen
        - std::nullptr_t
    
    Aufzählungen
    
        - unscoped enumerations ([i]enum-key[/i] = enum) - Aufzählungskonstanten werden im gleichen Scope wie die Aufzählung selbst plaziert
        - scoped enumerations ([i]enum-key[/i] = enum class / enum struct) - Aufzählung bildet einen eigenen Scope, in dem sich die Aufzählungskonstanten befinden, keine implizite Konvertierung in integer
    
    Aufzählungstypen haben einen zugrundeliegenden integralen Typen (underlying type), der für die Repräsentation verwendet werden kann.
    Dieser kann explizit angegeben werden (enum-base), wird er nicht angegeben, so ist er int im Falle von scoped Aufzählungen. In diesen Fällen ist der zugrundeliegende Typ fest (fixed).
    Im Falle von unscoped Aufzählungen ohne Angabe ist der Typ unspezifiziert mit bestimmten Einschränkungen (Details in 7.2/6), in der Praxis typischerweise int oder - soweit erforderlich - ein größerer Typ.
    
    Aggregate (aggregates)
    
        - Arrays
        - Klassen
            x ohne vom Nutzer deklarierte Konstruktoren
            x ohne nicht-statische protected oder private Datenmember
            x ohne Basisklassen
            x ohne virtuelle Funktionen
            x ohne Initialisierer für nichtstatische Member
    
    POD (plain old data) - rekursive Definition:
    
        - Skalare Typen
        - POD-Klasse
            x Klassen-Aggregat
            x ohne vom Nutzer deklarierten Destruktor
            x ohne vom Nutzer deklarierten Zuweisungsoperator
            x ohne nichtstatische nicht-POD-Datenmember
            - union: POD-union
            - Struktur: POD-struct
        - Arrays aus PODs
    Alle POD-Typen sind trivial und haben Standard-Layout.
    
    Literaltypen (literal types)
    
        - Skalare Typen
        - Referenzen auf Literaltypen
        - Array aus Literalen
        - Klassen
            x trivialer Destruktor
            x alle Initialisierer für nichtstatische Member (sofern vorhanden) sind konstante Ausdrücke
            x Entweder
                - Aggregat
                - mindestens eine constexpr-Konstruktor, der kein Copy- oder Movekonstruktor ist
            x alle nichtstatischen Datenmember und Basisklassen sind Literaltypen
    
    Trivial kopierbare Typen (trivially copyable types 3.9/9)
    
        - Skalare Typen
        - Trivial kopierbare Klassen
            x kein nicht-trivialer Copy-Konstruktor*
            x kein nicht-trivialer Move-Konstruktor*
            x kein nicht-trivialer Copy-Zuweisungsoperator*
            x kein nicht-trivialer Move-Zuweisungsoperator*
            x trivialer Destruktor*
        - Arrays solcher Typen
    
    Triviale Typen (trivial types 3.9/9)
    
        - Skalare Typen
        - Triviale Klassen
            x trivial kopierbare Klasse
            x trivialer Defaultkonstruktor
        - Arrays solcher Typen
    Alle trivialen Typen sind trivial kopierbar.
    
    Standardlayout-Typen (standard-layout types)
    
        - Skalare Typen
        - Standardlayout Klassen
            x nichtstatische Daten-Member haben Standardlayout
            x Basisklassen haben Standardlayout
            x keine virtuellen Funktionen
            x keine virtuellen Basisklassen
            x gleiche Zugriffskontrolle für alle nichstatischen Datenmember
            x höchtens 1 Klasse in der gesamten Vererbungshierarchie definiert nichtstatische Daten-Member
            x 1. Daten-Member (wenn vorhanden) ist nicht gleichzeitig Basisklasse
        - Arrays solcher Typen
    
    UDT (user defined types)
    
        - Klassen
        - Aufzählungen
    
    "eingebaute Typen" (build-in types): informell
    
        - Typen, die keine UDTs sind
    
    triviale Memberfunktionen
    -------------------------
    Eine spezielle Memberfunktion ist user-provided, wenn sie explizit deklariert wird, und diese 1. Deklaration weder explizit defaulted noch explizit deleted ist.
    Zur Vereinfachung im Folgenden:
    Eine Subobjektklasse sei eine Klasse, bei der es sich entweder um eine (direkte) Basisklasse oder den Klassentyp eines nichtstatischen Members, oder den Klassentype eines Elementes eines nichtstatischen Memberarrays handelt.
    
    Eine spezielle Memberfunktion ist trivial, wenn
        x sie nicht user-provided ist,
        x korrespondierende Memberfunktionen aller Subobjektklassen trivial sind,
        x im Falle des Defaultkonstruktors kein nichtstatischer Member über einen Initialisierer verfügt,
        x und
            - im Falle des Destruktors dieser nicht virtuell ist, sonst
            - die Klasse keine virtuellen Funktionen und keine virtuellen Basisklassen hat
    
    Korrespondierende Memberfunktionen i.o.S. sind
    - im Falle eines Defaultkonstruktors
         - die Defaultkonstruktoren der Subobjektklassen
    - im Falle des Destruktors
         - die Destruktoren der Subobjektklassen
    - sonst
         - die Memberfunktionen, die für Copy-/Move der Subobjekte ausgewählt werden (dabei handelt es sich nicht notwendigerweise um Copy-/Move-Konstruktoren oder Zuweisungsoperatoren, allerdings können nur solche trivial sein)
    

Anmelden zum Antworten