2016-09-01 6 views

Antwort

9

ein hyperlinked C++ grammar Verwendung, das Parsen von decltype(void()) ist:

decltype(expression) 
decltype(assignment-expression) 
decltype(conditional-expression) 

... viele Schritte umfassen, um von Operationen hier gehen ...

decltype(postfix-expression) 
decltype(simple-type-specifier (expression-listopt)) 
decltype(void()) 

So void() ist eine Art von expression hier insbesondere ein postfix-expression.

Insbesondere zitierte Abschnitt 5.2.3 [expr.type.conf] Absatz 2 der 2011 ISO C++ Standard:

Der Ausdruck T(), wo T ist ein einfach-Typ-Spezifizierer oder typename-Spezifizierer für einen nicht-Array vollständigen Objekttyp oder den (möglicherweise cv-qualifiziert) void Typen, schafft eine prvalue des angegebenen Typs, der Wert initialisiert ist (8,5; keine Initialisierung wird für den void() Fall getan).

So void() ist ein Ausdruck des Typs void, wie int() ist ein Ausdruck des Typs int (mit Wert 0). Offensichtlich hat ein void Ausdruck keinen Wert, aber hier ist es der Operand von decltype, also wird es nicht ausgewertet. decltype bezieht sich nur auf seinen Operandentyp, nicht auf seinen Wert.

decltype(void()) ist einfach eine ausführliche Art der Bezugnahme auf den Typ void.

+2

@skypjack: Siehe den C++ 11-Standard (oder einen Entwurf), Abschnitt 5.2.3 [expr.type.conv], Absatz 2. Ein * simple-type-specifier * gefolgt von leeren Klammern "erstellt einen prvalue der spezifizierter Typ, der valueinitialized ist (8.5; für den Fall void() wird keine Initialisierung durchgeführt) ". Genau wie 'int()' ein Ausdruck vom Typ 'int' ist, ist' void() 'ein Ausdruck vom Typ' void'. Und da es der Operand von "declltype" ist, wird es nicht ausgewertet. 'declltype (void())' ist nur eine komplexe Art, auf den Typ 'void' zu verweisen. (Yakk, du möchtest vielleicht deine Antwort erweitern, um zu erklären, wie 'void()' ein Ausdruck ist.) –

+1

@Yakk Wie bereits in den Kommentaren erwähnt, würde das Erweitern der Antwort mit mehr Details helfen. +1, um den Vorschlag zu fördern. Vielen Dank. – skypjack

+3

Ich habe mir erlaubt, eine Erklärung hinzuzufügen, was 'void()' bedeutet. Bitte überprüfe mein Update auf Richtigkeit. –

4

Ich zitiere die comment von @JoachimPileborg, die es zu erklären, scheint richtig:

Ich glaube, ich es jetzt herausgefunden, braucht decltype einen Ausdruck, und kein Typ. void() ist hier nicht wirklich ein Typ, sondern ein Ausdruck, ein C-Style-Cast (genau wie zum Beispiel int (12.34)) void (void) ist kein Ausdruck, daher funktioniert es nicht. Wie der Compiler verschiedene Dinge analysiert, hängt vom Kontext ab, wenn er einen Typ erwartet, der als ein Typ analysiert wird, wenn er einen Ausdruck erwartet, der als Ausdruck analysiert wird. sizeof() (mit den Klammern) erwartet zunächst einen Typ, ansonsten wird es als Klammerausdruck geparst.

Ich bin nicht auf der Suche nach Krediten oder Reputation.
Wie auch immer, ich denke, das war eine interessante Antwort in der Antwort, die eine eigene Frage für zukünftige Leser wert ist.

+0

Wenn Sie nicht rep wollen, können Sie die Antwort als Community Wiki markieren – AndyG

+0

@skypjack klicken Sie auf "bearbeiten" dann das Kontrollkästchen "Community Wiki" unter dem Textfenster – TemplateRex

+2

'void()' ist kein C-Stil Besetzung.In C besteht ein Cast aus einem Namen in Klammern, gefolgt von einem Ausdruck, zum Beispiel '(void) 42'. In 'void()' ist der Typname nicht geklammert, und auf ihn folgt kein Ausdruck. –

Verwandte Themen