Kann int (*)[]
ein unvollständiger Typ sein?
C 2018 6.2.5 1 sagt:
An verschiedenen Stellen innerhalb einer Übersetzungseinheit kann ein Objekttyp unvollständig (ohne ausreichende Informationen zur Bestimmung der Größe von Objekten dieses Typs) oder vollständig (mit ausreichenden Informationen) sein.
Wenn also die Größe eines Typs bekannt ist, scheint der Typ vollständig zu sein. 6.2.6.1 28 gibt an, dass bestimmte Zeigertypen dieselbe Größe haben müssen (Zeiger auf void
und Zeichen, Zeiger auf kompatible Typen, Zeiger auf Strukturen und Zeiger auf Gewerkschaften), Zeiger auf andere Typen können jedoch variieren.
In einer C-Implementierung, in der alle Zeiger oder alle Zeiger auf Arrays von int
dieselbe Größe haben, ist die Größe von int (*)[]
bekannt, sodass sie vollständig wäre. In einer Implementierung, die beispielsweise unterschiedliche Zeiger für große Arrays verwendet, ist die Größe nicht bekannt, sodass sie unvollständig ist.
Wie MM hervorhebt, darf eine Struktur kein Element mit unvollständigem Typ enthalten, mit Ausnahme eines endgültigen flexiblen Array-Elements gemäß einer Einschränkung in 6.7.2.1 3. Dies legt nahe, dass eine Implementierung mit einer Zeigergröße akzeptiert werden muss, struct { int (*p)[]; }
während eine Implementierung eine andere hat Größen für solche Arrays müssen eine Einschränkungsverletzung diagnostizieren. (Dies bedeutet wiederum, dass eine solche Erklärung nicht Teil der strikten Einhaltung von C ist.)
quelle
void *
vollständig ist, zeigt, dass ein Zeiger auf einen unvollständigen Typ vollständig sein kann. Es wird nicht angezeigt, ob ein Zeiger auf einen unvollständigen Typ unvollständig sein kann. Wenn man fragt: "Kann ein Säugetier ein Elefant sein?", Wenn man zeigt, dass "Ein Löwe ein Säugetier ist", würde dies nicht bedeuten, dass ein Säugetier kein Elefant sein kann. Die Frage fragt, ob die Menge X von Zeigern auf unvollständigen Typ ein Element enthalten kann, das unvollständig ist. Es ist irrelevant zu zeigen, dass die Menge X von Zeigern auf unvollständigen Typ ein Element enthält, das vollständig ist.Antworten:
Ein Array unbekannter Größe ist unvollständig:
Der Typ ist
int (*)[]
jedoch nicht unvollständig: Es ist ein Zeiger auf ein Arrayint
unbekannter Größe.Und ein Zeiger hat eine bekannte Größe:
Darüber hinaus können Sie es dank der Array-Semantik sogar dereferenzieren:
Bearbeiten
Außerdem ist ein Zeiger immer ein vollständiger Typ. Es ist in 6.2.5 / 20 schwarz auf weiß geschrieben:
quelle
printf
zeigt nur, dass ein Zeiger auf ein unvollständiges Array in der Implementierung, in der es ausgeführt wurde, vollständig ist, wie in der Frage angegeben. Ohne 6.2.5 20, wie im letzten Absatz angegeben, kann er möglicherweise nicht kompiliert werden. 6.2.5 23 ist ebenfalls nicht relevant; Es sagt uns, dass die Größe bekannt und konstant ist, wenn sie vollständig ist, und wir wissen bereits, dass die Größe bekannt ist, wenn sie vollständig ist.int
dieselbe Größe haben, und alle Zeiger auf Arrays einer bestimmtenstruct
Größe müssen dieselbe Größe haben, obwohl möglicherweise nicht alle Zeiger auf Arrays unterschiedlicher Artstruct
dieselbe Größe haben müssen wie einander.T(*)[]
es die gleiche Größe haben muss wieT(*)[5]
, da es sich um kompatible Typen handelt und wir Qualifikationsmerkmale hinzufügen oder entfernen könnten