这种C标准的标记方法是否符合标准?

(对于指针标记的重述:其中对象的大小意味着其指针中的有限位数将始终未使用,并且可以重新用于其他用途,例如标记对象的类型.)

excellent answer到我的previous question在这个问题上证实,将指针转换为整数和对整数进行处理的天真的方法在技术上不能依赖于工作(不考虑其在实践中的流行度).

再考虑一下,我想我有一个解决方案适用于原始问题中描述的具体情况(所有对象的大小相同,所有对象都从单个“堆”数组分配).有人可以确认我的推理吗

// given:
typedef Cell ...; // such that sizeof(Cell) == 8
Cell heap[1024];  // or dynamic,w/e

// then:
void * tagged = ((char *)&heap[42]) + 3;  // pointer with tag 3 (w/e that means)

int tag = ((char *)tagged - (char *)heap) % sizeof(Cell);  // 3
Cell * ptr = (Cell *)((char *)tagged - tag);               // &heap[42]

换句话说:没有关于指针的整数表示的假设.通过索引指向对象中的字节来应用标记. (这肯定是允许的.)

指针减法返回相同数组中两个对象的索引的差异.对象内的字节地址应该是连续的,因此通过获取寻址字节的索引并从该索引中删除所有以前的所有单元格的大小,将标记的值转换为标签;标记的指针可以通过删除现在已知的索引偏移量来还原到单元格指针.

这是否符合标准,因此是一种便携式的指针标记方法?如果在这种情况下将数组的类型转换为其他字符,则指针减法是否仍然可以工作?我可以这样使用sizeof(Cell)吗?

(不,我不知道为什么这个技术性在我心中好多了,是的,可移植性很容易通过其他方式实现.)

解决方法

在这里,我认为唯一需要更加谨慎的是整数类型.不要使用int:

>指针差异的正确类型是ptrdiff_t.
> sizeof的结果是size_t为无符号类型
>你在size_t类型和ptrdiff_t之间做%,所以结果最可能是size_t,所以是一个无符号的值
>将size_t转换为int是实现定义的(所以不可移植),通常它只会丢弃高位位

int将会工作很长时间,但是在64位处理器上使用非常大的阵列的那一天,你会后悔(经过几天的调试)

相关文章

本程序的编译和运行环境如下(如果有运行方面的问题欢迎在评...
水了一学期的院选修,万万没想到期末考试还有比较硬核的编程...
补充一下,先前文章末尾给出的下载链接的完整代码含有部分C&...
思路如标题所说采用模N取余法,难点是这个除法过程如何实现。...
本篇博客有更新!!!更新后效果图如下: 文章末尾的完整代码...
刚开始学习模块化程序设计时,估计大家都被形参和实参搞迷糊...