C++将 2 个或更多地址超过数组末尾是否合法
C++ is it legal to take the address of 2 or more past the end of the array?
From 通过下标获取一个过去结束数组元素的地址:C++标准是否合法?
似乎有语言专门用于获取一个而不是数组端的地址。
如果不去引用,为什么 2 或 2,000,000 过了最后会是一个问题?
看一些简单的循环:
int array[];
...
for (int i = 0: i < array_max; ++i)
{
int * x = &array[i *2]; // Is this legal
int y=0;
if (i * 2 < array_max) // We check here before dereference
{
y = *x; // Legal dereference
}
...
}
为什么或在什么时候变得未定义,在实践中它只是将 ptr 设置为某个值,如果不引用,为什么它会未定义?
更具体地说 - 除了预期会发生什么之外,还有什么例子可以?
将地址带到数组末尾之外的关键问题是分段体系结构:您可能会溢出指针的可表示范围。现有规则已经造成了一定程度的痛苦,因为这意味着最后一个对象不能位于段的边界上。但是,形成此地址的能力已经确立。
由于array[i *2]
等价于*((array) + (i*2))
,我们应该看看指针添加的规则。C++11 §5.7 说:
如果指针操作数和结果都指向同一数组对象的元素,或者指向数组对象的最后一个元素,则计算不应产生溢出;否则,行为是未定义的。
因此,即使您不在指针上执行间接寻址,您也有未定义的行为(更不用说您确实执行了间接寻址,因为我在开头给出了表达式等效性)。
实际上,它只是将PTR设置为某个值
从理论上讲,只允许使用指向无效位置的指针。
指针不是整数:它们是指向其他事物或空性的东西。
您不能将它们设置为您喜欢的任何数字。
在此示例中,只有赋值,然后限定取消引用 - 该值仅在验证时才使用,问题是为什么值的设置是一个问题?
是的,你必须非常不幸才能遇到这样做的实际后果。"未定义的行为"并不意味着"总是崩溃"。为什么标准实际上应该强制要求此类操作的语义?你认为这样的语义应该是什么?
相关文章:
- 如何找到大小'x'数组是否完全填充,在C++?
- 任意大小的 constexpr 数组是否可以用作 switch 语句中的案例?
- 在 constexpr 构造函数中初始化数组是否合法?
- 以这种方式初始化的 char 数组是否会自动添加空终止符?
- 检查反向数组是否与原始数组相同
- 如何检查二维字符数组是否有空字
- 检查数组是否等于的最快方法?
- 确定数组是否可以旋转 3 个连续的数组元素进行排序?
- 如何检查数组是否包含多个元素?
- 我在代码中收到一个运行时错误,该错误如何通过修改最多一个元素来查找数组是否可以变得不减少
- c ++ 如何断言 char 数组与否,检查 char 数组是否以 "0" 开头或包含"0"
- 下课时的数组是否可以正常工作?
- C++全局常量数组:是否保证合并(优化)到一个副本中
- 在 C++17 中声明大小为 0 的数组是否合法
- 如果在执行过程中替换二进制文件,"const"数组是否驻留在内存中?
- 临时数组是否可能
- 使用二维数组作为一维数组是否正确?可能会导致未定义的行为左右?
- 当有多个查询时,检查某些子数组是否排序的有效方法是什么?
- 用于检查 char 数组是否仅包含允许的字符的函数
- 检查数组是否'right' (C++)