size_t是否便携?

问题描述:

GCC 4.4.1,C99size_t是否便携?

我使用size_tsize_tunsigned int。但是,这取决于您是否正在运行32位或64位。

我将使用size_t来存储缓冲区的大小。

所以我不认为这将是非常便携,如果跨架构使用。

只是一个问题,在32位或64位上使用size_t。什么情况会导致最严重的问题?

size_t保证是能够保持您的实现任何对象的字节数。 这就是为什么返回类型sizeofsize_t

所以,是的,它是便于携带。

+7

只要您不尝试将size_t类型变量保存为二进制文件或通过网络连接发送,size_t便携。你开始做的第二件事就是将它作为一种非常不可移植的东西,它被粘在地板上。 – 2012-06-13 09:30:34

唯一真正严重的问题是试图访问一个相当大的数组或size_t的大数。

就像一个普通的“int”在64位上可能就足够了,但是可能会导致32位崩溃,因为它在32位系统上对于int来说太大了。

如果您使用malloc()或read(),对缓冲区使用size_t或ssize_t是有意义的。为便携,请使用SIZE_MAX,SSIZE_MAX,sizeof(输入您的缓冲区)和%zd或%zu printf()。

+0

不幸的是,微软的C编译器不支持'z'大小改性剂'的printf()'。 – Novelocrat 2009-11-08 17:03:17

+0

'z'修饰符是C99标准的一部分。迄今为止,微软编译器使用C89/90。在C89/90中,size_t打印的“可移植性”必须手动实现。 – AnT 2009-11-08 17:17:09

+0

那些bas ...,我忘了。那么,他确实询问了C99。我猜他确实询问了“最严重”的问题,这个问题可能是Linux的乐观分配,或者轻率地假设(count * sizeof())不会溢出,或者可能认为您首先需要分配那么多内存。 – paul 2009-11-08 17:22:57

你不应该认为size_t是一个无符号整数(see this answer),但我认为它在两种架构上都有相同的范围。

取决于你正在使用size_t。

如果使用它来确定内存缓冲区的大小,它将是安全的,因为size_t足够大,可以解决任何计算机的整个内存问题。因此,如果内存缓冲区大于此值,则无论如何您都有问题。另一方面,如果将其用作通用无符号整数来计算Universe中的星号数,则可能在32位系统上出现问题(不确定64位系统)。

+0

不正确。 'size_t'足以保存实现支持的最大对象的大小。 'size_t'不足以解决整个内存。对于后者,你需要'intptr_t' /'uintptr_t'。 – AnT 2009-11-08 16:54:24

+0

我站好了。但是,最大的对象就是你在这种情况下可能需要的东西,否则你有另一个问题。 – Jonatan 2009-11-08 16:55:50

您还得到了off_t和ptrdiff_t/ssize_t,它们在架构之间以相同的方式不同。

如果您正确使用它们,那么它们可跨架构移植。在32位系统中,它们都是32位宽,而在64位系统中它们都是64位宽。这就是你想要的 - 在32位系统上,缓冲区的大小不可能大于32位size_t,但在64位系统上它可能会大得多。

你不应该使用整数,长整型或其他任何东西。除此之外,长度的大小取决于平台(大多数32位系统上的32位,64位Unix系统上的64位,64位Windows上的32位)。

在这种情况下很难弄清楚“便携式”的含义。术语“便携式”允许多种不同的解释。

类型size_t有一个非常具体的目的。它可以保存给定实现中的任何对象的大小。即它总是可以接收到sizeof()运算符的结果。类型size_t没有其他目的,并且在其预期的应用程序中它是100%便携式的,就像任何东西一样便携。

你问的是什么样的“便携式”又一次不清楚。

+0

我正在使用size_t来获取缓冲区的大小。我使用套接字编程做了一些消息传递,源代码将在Linux和Windows上编译。我将不得不获取从客户端发送的数据的size_t。谢谢 – ant2009 2009-11-08 17:55:31

+0

@robUK,你应该为你的问题添加这条重要的信息。 – quinmars 2009-11-08 23:33:53

正如其他人所说,size_t是正确的,完全可以接受的结果sizeof()或任何可表示的对象的大小以字节为单位。你有什么需要注意的是:

  1. size_t,其大小与一些无符号整型相同。它不一定是相同的字节数作为最大的无符号整数类型,unsigned intunsigned long的等
  2. sizeof(size_t)是如此memcpy实现定义的字节数“荷兰国际集团,或分配到比其他uintmax_t任何整数类型是馊主意。我甚至不确定是否可以安全地假设它的尺寸相同或比uintmax_t小。
  3. size_t值写入二进制文件并将其读取回size_t由另一个进程,在不同的机器上,或通过使用不同的编译器选项编译的某些内容可能会危害您的健康。
  4. 通过网络发送一个size_t值并试图使用上的另一侧的sizeof(size_t)缓冲器以接收这是相当不安全的。

所有这些都是任何其他整数类型的标准问题,除了unsigned char。所以size_t就像任何其他整数类型一样便携。