7

在我的平台上(我认为在大多数平台上)std::size_t并且std::ptrdiff_t 具有相同的大小和相同的对齐方式。有没有不正确的平台?简而言之:标准是否要求?

4

3 回答 3

6

简而言之:标准是否要求?

不,唯一的要求来自[support.types.layout]/2,它是:

ptrdiff_t 类型是实现定义的有符号整数类型,可以保存数组对象中两个下标的差异,如 [expr.add] 中所述。

第4段

[ 注意:建议实现为 ptrdiff_t 和 size_t 选择整数转换等级不大于signed long int 的类型,除非需要更大的大小来包含所有可能的值。——尾注]

但是注释是非规范性的,它只是一个建议,而不是一个要求。


std::size_t定义为

size_t 类型是实现定义的无符号整数类型,它大到足以包含任何对象 ([expr.sizeof]) 的字节大小。

第 3 段中,也没有要求它们相同。

于 2020-05-21T13:51:38.847 回答
3

标准没有要求。

请注意,当前的英特尔处理器有 48 位指针。

所以就我个人而言,我认为unsigned为. 虽然这样的计划实施起来会很头疼。std::size_tstd::ptrdiff_t

更有趣的是,一旦芯片组发展为具有 64 位指针(我们离必要的还有一段距离),大概std::ptrdiff_t必须至少是 65 位!因此,我个人记住,一天sizeof(std::ptrdiff_t)可能大于sizeof(std::size_t).

于 2020-05-21T14:36:13.130 回答
0

在我的平台上......std::size_t并且std::ptrdiff_t具有相同的大小

这是如何合规的?

C 有(我相信 C++ 继承了 - 如果不让我知道删除)在§ J.2 中作为 UB:

两个指针相减的结果无法在类型ptrdiff_t(6.5.6) 的对象中表示。”

这允许类型ptrdiff_t成为 unsigned 的已签名副本size_t
当这样配对没有填充时,

char a[PTRDIFF_MAX + (size_t)1];         // OK with enough memory in the location needed
size_t size_a = sizeof a;                // OK             
size_t diff0 = &a[sizeof a - 1] - &a[0]; // OK
ptrdiff_t diff1 = &a[sizeof a] - &a[0];  // UB
ptrdiff_t diff2 = %a[0] - &a[sizeof a];  // UB

故事的寓意:当数组元素计数超过时,指针减法(结果类型ptrdiff_t:)可能会出现问题。PTRDIFF_MAX

于 2020-05-21T23:37:53.913 回答