Wieso sizeof int ist falsch, während sizeof(int) ist die richtige?
Wissen wir, dass sizeof
ist ein operator, der verwendet wird für die Berechnung der Größe eines beliebigen Datentyp und Ausdruck, und wenn der operand ist ein Ausdruck, der von Klammern können weggelassen werden.
int main()
{
int a;
sizeof int;
sizeof( int );
sizeof a;
sizeof( a );
return 0;
}
ersten Nutzung sizeof
ist falsch, andere richtig.
Wenn es kompiliert wird mit gcc folgende Fehlermeldung gegeben:
main.c:5:9: error: expected expression before ‘int’
Meine Frage ist, warum der C-standard nicht ermöglichen, diese Art von operation. Wird sizeof int
Ursache von Mehrdeutigkeiten?
- Das lustige an der Sache ist, dass nicht alle Ausdrücke werden akzeptiert, ohne Klammern: versuchen
sizeof (int)a
. - OP ist zu Fragen, die Argumentation hinter dem standardese Zitate kennt er bereits die Zitate, die erwähnt werden markiert beantworten.
- Ich denke, das ist, weil eine Klammer nach dem "sizeof" wird interpretiert als Teil der sizeof-operator, anstatt GEHÖRIG etwas auf den rest des Ausdrucks (die hätte den Typ-cast-operator). Wenn also verstehe ich das richtig, Sie hätte etwas geschrieben zu verdecken wie
sizeof *&(int)a
und dann wäre es okay gewesen, da wir am Ende mit einem Ausdruck, und nicht eine Art. sizeof +(int)a
hat den Vorteil, über*&
tatsächlich kompilieren 😉- Ah stimmt, es ist kein lvalue. Wenn er kompilieren in Embarcadero C++, seltsam genug. Trotzdem glaube ich, dass wir gerade jetzt eine Verwendung für den unären + - operator! Das muss das erste mal in der Geschichte der C-Programmierung 🙂
- Sie haben noch vorsichtig sein mit dem unären
+
. Zum Beispielsizeof +(char)a == sizeof(int)
aufgrund von integer-promotion, ist es wahrscheinlich weniger Fehler-anfällig nur zu setzen in die Klammern, wenn es irgendeine Sorge über den Ausdruck, den Sie versuchen zu nehmen, die Größe. Also ich bin mir nicht sicher, ich würde so weit gehen, nennen es "Verwendung", obwohl ich zugeben, ich habe es zu benutzen... - In der Tat. All das ist hervorragendes material für die IOCCC, aber vielleicht nicht für real life-code 🙂
- lassen Sie uns weiter, diese Diskussion im chat
Du musst angemeldet sein, um einen Kommentar abzugeben.
Den folgenden, könnte mehrdeutig sein:
Ist, dass
(sizeof (int*)) + 1
oder(sizeof(int)) * (+1)
?Offensichtlich die Programmiersprache C könnte eine Regel eingeführt, um diese Mehrdeutigkeit aufzulösen, aber ich kann mir vorstellen, warum es nicht zu stören. Mit der Sprache, wie es steht, ein Typ Bezeichner erscheint nie "nackt" in einem Ausdruck, und so gibt es keine Notwendigkeit für Regeln zu lösen, ob das zweite
*
ist Bestandteil der Art oder ein arithmetischer operator.Die bestehende Grammatik nicht bereits lösen, die potenzielle Mehrdeutigkeit von
sizeof (int *) + 1
. Es ist(sizeof(int*))+1
, nichtsizeof((int*)(+1))
.C++ hat ein etwas ähnliches Problem zu lösen mit der function-style-cast-syntax. Schreiben Sie
int(0)
und Sie können schreibentypedef int *intptr; intptr(0);
, aber Sie können nicht schreibenint*(0)
. In diesem Fall, die Auflösung ist, dass das "Nackte" Typ muss ein einfacher Typ name, es kann sich nicht einfach irgendwelche alten Typ-id, die möglicherweise Leerzeichen oder nachfolgende Satzzeichen. Vielleichtsizeof
könnte definiert wurden, mit der gleichen Einschränkung, ich bin mir nicht sicher.new int*(X)
wäre mehrdeutig, wenn C++ nicht angeben, dass der neue Betreiber übernimmt den längsten string, der möglicherweise einen geben. Also In C++ - Sie hätten das gleiche mit sizeof, denke ich. Aber in C++ kann man sagensizeof int()
was dann gewesen wäre mehrdeutig (Typ oder Wert initialisiert int?).sizeof int()
wäre schlecht gebildet ("keineoperator()
fürsize_t
"), die ich erwarten würde unerwünscht!Vom C99-Standard
In Ihrem Fall
int
ist weder der Ausdruck noch die eingeklammerten Namen.int;
kompiliert, so daß ich falsch aber, dass es sein muss auch ein expression. Nach der Einnahme eines Blick auf Ihre standard bezeichnet, es stellt sich heraus, dass es ein paar Grammatik-Regeln (6.7):declaration: declaration-specifiers init-declarator-list[opt] ;
,declaration-specifiers: type-specifier declaration-specifiers[opt]
, undtype-specifier: int
definierenint;
als declaration, nicht expression ([opt] bedeutet optional). Vielen Dank für das Zitat und verknüpfte Dokument.Gibt es zwei Möglichkeiten der Verwendung des sizeof-operator in C. Die syntax ist:
Wenn Sie einen Typ als Operanden, müssen Sie die Klammer, indem Sie die syntax der definition der Sprache. Wenn Sie die Verwendung von sizeof auf einen Ausdruck, Sie brauchen nicht die Klammer.
C-standard gibt ein Beispiel, wo Sie möchten möglicherweise verwenden Sie es auf einem Ausdruck:
Jedoch aus Gründen der Einheitlichkeit und vermeiden Sie Fehler im Zusammenhang mit operator-Vorrang, würde ich persönlich rate immer () egal, die situation.
sizeof expression
undsizeof(type)
erläutert in dieser Antwort.