sizeof(数组)如何工作
c在运行时如何find数组的大小? 数组的大小或数组边界的信息存储在哪里?
sizeof(array)
完全由C编译器实现。 当程序被链接时,看起来像sizeof()
调用的东西已经被转换成一个常量。
例如:当你编译这个C代码时:
#include <stdlib.h> #include <stdio.h> int main(int argc, char** argv) { int a[33]; printf("%d\n", sizeof(a)); }
你得到
.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
中间的$132
是数组的大小,132 = 4 * 33。请注意,没有call sizeof
指令 – 与printf
不同,它是一个真正的函数。
在C99之前,sizeof是C ++和C中的纯编译时间。 从C99开始有可变长度的数组:
// returns n + 3 int f(int n) { char v[n + 3]; // not purely a compile time construct anymore return sizeof v; }
这将评估操作数的sizeof
,因为n
在编译时还不知道。 这只适用于可变长度的数组:其他操作数或types仍然在编译时进行sizeof计算。 特别是在编译时已知尺寸的数组仍然像C ++和C89一样处理。 因此, sizeof
返回的值不再是编译时间常量(常量expression式)。 你不能在需要这样的值的地方使用它 – 例如当初始化静态variables时,除非编译器特定的扩展允许它(C标准允许实现具有对常量的扩展)。
sizeof()
只适用于一个固定大小的数组(可以是静态的,基于堆栈的或在一个结构体中)。
如果将其应用于使用malloc
(或C ++中的new)创build的数组,则将始终获取指针的大小。
是的,这是基于编译时间的信息。
sizeof
给出了variables的大小,而不是指向的对象的大小(如果有的话) sizeof(arrayVar)
将返回数组大小,当且仅当arrayVar
在数组中作为数组而不是一个指针。
例如:
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)
在编译时查找sizeof(Array),而不是在运行时查找。 信息不存储。
你有兴趣实现边界检查吗? 如果是这样的话,有很多不同的方法可以解决这个问题。