2009-03-22 8 views

Antwort

55

sizeof(array) wird vollständig von dem C-Compiler implementiert. Zu dem Zeitpunkt, zu dem das Programm verknüpft wird, wurde das, was wie ein sizeof()-Aufruf an Sie aussieht, in eine Konstante konvertiert.

Beispiel: wenn Sie diesen Code C kompilieren:

#include <stdlib.h> 
#include <stdio.h> 
int main(int argc, char** argv) { 
    int a[33]; 
    printf("%d\n", sizeof(a)); 
} 

Sie erhalten

.file "sz.c" 
    .section  .rodata 
.LC0: 
    .string "%d\n" 
    .text 
.globl main 
    .type main, @function 
main: 
    leal 4(%esp), %ecx 
    andl $-16, %esp 
    pushl -4(%ecx) 
    pushl %ebp 
    movl %esp, %ebp 
    pushl %ecx 
    subl $164, %esp 
    movl $132, 4(%esp) 
    movl $.LC0, (%esp) 
    call printf 
    addl $164, %esp 
    popl %ecx 
    popl %ebp 
    leal -4(%ecx), %esp 
    ret 
    .size main, .-main 
    .ident "GCC: (GNU) 4.1.2 (Gentoo 4.1.2 p1.1)" 
    .section  .note.GNU-stack,"",@progbits 

The $132 in der Mitte der Größe des Arrays ist, 132 = 4 * 33. Beachten Sie, dass es keine call sizeof Anweisung - im Gegensatz zu printf, die eine echte Funktion ist.

+1

lol! Das bringt mir bei, nicht zu überprüfen, dass ich meine Hände an den richtigen Ort gelegt habe ...Danke für die Fix Rob –

+1

Ah, ich sehe jetzt, David muss eine Blind Touch Typist mit einer taktilen Dysfunktion in den Enden seiner Finger sein :-) Lustig, wie die c und e waren in Ordnung - ich musste überprüfen, dass jeder andere Brief war eine links von der richtigen Position. – paxdiablo

+1

Ich vermute, meine linke Hand war am richtigen Platz, aber meine rechte Hand wurde um eine Taste nach links verschoben ... scheint ein leichter Fehler zu sein - wenn Sie beim Fernsehen eine Antwort tippen ;-) –

7

sizeof() funktioniert nur für ein Array fester Größe (die statisch, stack-basiert oder in einer Struktur sein kann).

Wenn Sie es auf ein Array anwenden, das mit malloc (oder neu in C++) erstellt wurde, erhalten Sie immer die Größe eines Zeigers.

Und ja, das basiert auf Kompilierzeit Informationen.

+0

Arrays mit fester Größe sind nicht unbedingt stapelbasiert. C hat keinen neuen Operator. – ysth

+0

Sie haben Recht, ich werde ein wenig bearbeiten. –

+3

Sie haben C99 VLA - Arrays variabler Länge vergessen. –

2

sizeof (Array) wird zur Kompilierzeit gesucht, nicht zur Laufzeit. Die Information wird nicht gespeichert.

Sind Sie vielleicht daran interessiert, die Überprüfung von Grenzwerten zu implementieren? Wenn dies der Fall ist, gibt es eine Reihe verschiedener Möglichkeiten, dies zu tun.

5

sizeof gibt die Größe der Variablen, nicht die Größe des Objekts, das Sie zeigt auf (wenn es einen gibt.) sizeof(arrayVar) die Array-Größe in Bytes zurück, wenn und nur wenn arrayVar in Umfang als deklariert Array und kein Zeiger.

Zum Beispiel:

char myArray[10]; 
char* myPtr = myArray; 

printf("%d\n", sizeof(myArray)) // prints 10 
printf("%d\n", sizeof(myPtr)); // prints 4 (on a 32-bit machine) 
17

sizeof ist reine Kompilierzeit in C++ und C vor C99. Beginnend mit C99 gibt es variabler Länge Arrays:

// returns n + 3 
int f(int n) { 
    char v[n + 3]; 

    // not purely a compile time construct anymore 
    return sizeof v; 
} 

dass die sizeof Operanden auswerten wird, weil n noch nicht zum Zeitpunkt der Kompilierung bekannt. Das nur gilt für Arrays mit variabler Länge: Andere Operanden oder Typen machen immer noch sizeof compute zum Zeitpunkt der Kompilierung. Insbesondere werden Arrays mit zur Kompilierungszeit bekannten Dimensionen immer noch wie in C++ und C89 behandelt. Daher ist der von sizeof zurückgegebene Wert keine Kompilierzeitkonstante (konstanter Ausdruck) mehr. Sie können ihn nicht verwenden, wenn ein solcher Wert benötigt wird - zum Beispiel beim Initialisieren von statischen Variablen, es sei denn, eine Compiler-spezifische Erweiterung erlaubt dies (der C-Standard erlaubt einer Implementierung, Erweiterungen zu haben, was sie als Konstante behandelt).

+4

Gut, dass Sie erwähnen C99-VLAs. Ihre Antwort sollte jedoch betonen, dass selbst in C99 die Größe von Arrays mit fester Größe zur Kompilierungszeit berechnet wird - nur VLAs werden zur Laufzeit berechnet. Als Konsequenz kann man "sizeof (array)" nicht immer als Konstante in C99 verwenden. –

+0

oh richtig. Ich habe diese Zweideutigkeit in meiner Antwort nicht gesehen. –

+0

ok, bitte Bettzeit für mich. später werde ich aufwachen und über all diese Tippfehler in meinen Antworten schreien: p –