我和c中的size_t搞混了,我知道它是由sizeof操作符返回的。但它究竟是什么?它是数据类型吗?
假设我有一个for循环:
for(i = 0; i < some_size; i++)
我应该用int I吗?或者size_t i;?
我和c中的size_t搞混了,我知道它是由sizeof操作符返回的。但它究竟是什么?它是数据类型吗?
假设我有一个for循环:
for(i = 0; i < some_size; i++)
我应该用int I吗?或者size_t i;?
当前回答
Since nobody has yet mentioned it, the primary linguistic significance of size_t is that the sizeof operator returns a value of that type. Likewise, the primary significance of ptrdiff_t is that subtracting one pointer from another will yield a value of that type. Library functions that accept it do so because it will allow such functions to work with objects whose size exceeds UINT_MAX on systems where such objects could exist, without forcing callers to waste code passing a value larger than "unsigned int" on systems where the larger type would suffice for all possible objects.
其他回答
Size_t是一种无符号整型数据类型,它只能赋0和大于0的整型值。它测量任何对象大小的字节,并由sizeof操作符返回。
Const是size_t的语法表示,但是没有Const你也可以运行程序。
const size_t number;
Size_t经常用于数组索引和循环计数。如果编译器是32位的,它将在unsigned int上工作。如果编译器是64位的,它也可以在unsigned long long int上工作。size_t的最大大小取决于编译器类型。
Size_t已经在<stdio.h>头文件中定义,但它也可以由 <stddef.h>, <stdlib.h>, <string.h>, <time.h>, <wchar.h>头文件。
示例(使用const)
#include <stdio.h>
int main()
{
const size_t value = 200;
size_t i;
int arr[value];
for (i = 0 ; i < value ; ++i)
{
arr[i] = i;
}
size_t size = sizeof(arr);
printf("size = %zu\n", size);
}
输出:size = 800
示例(不含const)
#include <stdio.h>
int main()
{
size_t value = 200;
size_t i;
int arr[value];
for (i = 0; i < value; ++i)
{
arr[i] = i;
}
size_t size = sizeof(arr);
printf("size = %zu\n", size);
}
输出:size = 800
根据我的理解,size_t是一个无符号整数,其位大小足以容纳本机体系结构的指针。
So:
sizeof(size_t) >= sizeof(void*)
要了解为什么size_t需要存在,以及我们是如何到达这里的:
在实用术语中,size_t和ptrdiff_t在64位实现中保证为64位宽,在32位实现中保证为32位宽,等等。他们不能在不破坏遗留代码的情况下,在每个编译器上强制任何现有类型意味着这一点。
A size_t or ptrdiff_t is not necessarily the same as an intptr_t or uintptr_t. They were different on certain architectures that were still in use when size_t and ptrdiff_t were added to the Standard in the late 1980s, and becoming obsolete when C99 added many new types but not gone yet (such as 16-bit Windows). The x86 in 16-bit protected mode had a segmented memory where the largest possible array or structure could be only 65,536 bytes in size, but a far pointer needed to be 32 bits wide, wider than the registers. On those, intptr_t would have been 32 bits wide but size_t and ptrdiff_t could be 16 bits wide and fit in a register. And who knew what kind of operating system might be written in the future? In theory, the i386 architecture offers a 32-bit segmentation model with 48-bit pointers that no operating system has ever actually used.
The type of a memory offset could not be long because far too much legacy code assumes that long is exactly 32 bits wide. This assumption was even built into the UNIX and Windows APIs. Unfortunately, a lot of other legacy code also assumed that a long is wide enough to hold a pointer, a file offset, the number of seconds that have elapsed since 1970, and so on. POSIX now provides a standardized way to force the latter assumption to be true instead of the former, but neither is a portable assumption to make.
它不可能是int型,因为在90年代只有极少数的编译器将int型设置为64位宽。然后,他们真的很奇怪,保持长32位宽。标准的下一个修订版本宣布int比long更宽是非法的,但在大多数64位系统上int仍然是32位宽。
它不能是long long int,这是后来添加的,因为即使在32位系统上,它也至少被创建为64位宽。
因此,需要一种新的类型。即使不是,所有这些其他类型也意味着数组或对象内的偏移量以外的东西。如果说从32位到64位迁移的惨败中有什么教训的话,那就是要明确类型需要具有哪些属性,而不是在不同的程序中使用意味着不同内容的属性。
如果你是经验主义者,
echo | gcc -E -xc -include 'stddef.h' - | grep size_t
输出Ubuntu 14.04 64位GCC 4.8:
typedef long unsigned int size_t;
注意,stddef.h是由GCC提供的,而不是GCC 4.2中src/ GCC /ginclude/stddef.h下的glibc。
有趣的C99外观
Malloc以size_t作为参数,因此它决定了可以分配的最大大小。 由于它也是由sizeof返回的,我认为它限制了任何数组的最大大小。 请参见:C语言中数组的最大大小是多少?
Size_t是无符号整数数据类型。在使用GNU C库的系统上,这将是unsigned int或unsigned long int。Size_t通常用于数组索引和循环计数。