以下使用涉及越界访问的指针算法的语句是否有效?
Are the following statements using pointer arithmetic involving out of bound aceess valid?
char array[8] = "Raining";
根据我的理解,我认为以下所有针对这些陈述的评论都是真实的。
char *p1 = array + 7; --> points to '[=11=]'
char *p2 = array + 8; --> undefined behaviour
char *p3 = array + 9; --> undefined behaviour
char *p4 = array + 10; --> undefined behaviour
我的理解对吗?
在你的情况下,
char *p1 = array + 7;
和
char *p2 = array + 8;
有效,因为,法律允许您指向
- 数组长度内的任何对象
- 最后一个数组元素之后的一个 直到您取消引用它。
OTOH,
char *p3 = array + 9;
和
char *p4 = array + 10;
未定义。
引用 C11
,章节 §6.5.6,"Additive operators"(强调我的)
[与 C99
、章节 §6.5.6/p8 相同,任何感兴趣的人]
When an expression that has integer type is added to or subtracted from a pointer, the
result has the type of the pointer operand. If the pointer operand points to an element of
an array object, and the array is large enough, the result points to an element offset from
the original element such that the difference of the subscripts of the resulting and original
array elements equals the integer expression. In other words, if the expression P
points to
the i
-th element of an array object, the expressions (P)+N
(equivalently, N+(P)
) and
(P)-N
(where N
has the value n
) point to, respectively, the i+n
-th and i−n
-th elements of
the array object, provided they exist. Moreover, if the expression P
points to the last
element of an array object, the expression (P)+1
points one past the last element of the
array object, and if the expression Q
points one past the last element of an array object,
the expression (Q)-1
points to the last element of the array object. If both the pointer
operand and the result point to elements of the same array object, or one past the last
element of the array object, the evaluation shall not produce an overflow; otherwise, the
behavior is undefined. [...]
由于 NULL 终止符,array
中有 8 个元素。
char *p1 = array + 7;
定义明确。
char *p2 = array + 8;
实际上是定义的。您可以设置一个指向数组的指针。 (只是不要取消引用它。)
另外两个未定义。不允许将指针设置为超出数组的一个。
第一行指向数组内的一个合法元素,第二行在解引用前一直有效。你剩下的 post 是对的。
char *p1 = array + 7; \-->points to '[=10=]', within array
char *p2 = array + 8; \-->defined behaviour until dereferenced
允许尾后寻址的原因是为了便于编写遍历整个数组的循环,例如,while (*d++ = *s++);
.
数组的边界标记描述了一个半开范围,从(并包括)第一个元素开始,到(但不包括)最后一个元素结束:[beginning,end)
。
char array[8] = "Raining";
根据我的理解,我认为以下所有针对这些陈述的评论都是真实的。
char *p1 = array + 7; --> points to '[=11=]'
char *p2 = array + 8; --> undefined behaviour
char *p3 = array + 9; --> undefined behaviour
char *p4 = array + 10; --> undefined behaviour
我的理解对吗?
在你的情况下,
char *p1 = array + 7;
和
char *p2 = array + 8;
有效,因为,法律允许您指向
- 数组长度内的任何对象
- 最后一个数组元素之后的一个 直到您取消引用它。
OTOH,
char *p3 = array + 9;
和
char *p4 = array + 10;
未定义。
引用 C11
,章节 §6.5.6,"Additive operators"(强调我的)
[与 C99
、章节 §6.5.6/p8 相同,任何感兴趣的人]
When an expression that has integer type is added to or subtracted from a pointer, the result has the type of the pointer operand. If the pointer operand points to an element of an array object, and the array is large enough, the result points to an element offset from the original element such that the difference of the subscripts of the resulting and original array elements equals the integer expression. In other words, if the expression
P
points to thei
-th element of an array object, the expressions(P)+N
(equivalently,N+(P)
) and(P)-N
(whereN
has the valuen
) point to, respectively, thei+n
-th andi−n
-th elements of the array object, provided they exist. Moreover, if the expressionP
points to the last element of an array object, the expression(P)+1
points one past the last element of the array object, and if the expressionQ
points one past the last element of an array object, the expression(Q)-1
points to the last element of the array object. If both the pointer operand and the result point to elements of the same array object, or one past the last element of the array object, the evaluation shall not produce an overflow; otherwise, the behavior is undefined. [...]
array
中有 8 个元素。
char *p1 = array + 7;
定义明确。
char *p2 = array + 8;
实际上是定义的。您可以设置一个指向数组的指针。 (只是不要取消引用它。)
另外两个未定义。不允许将指针设置为超出数组的一个。
第一行指向数组内的一个合法元素,第二行在解引用前一直有效。你剩下的 post 是对的。
char *p1 = array + 7; \-->points to '[=10=]', within array
char *p2 = array + 8; \-->defined behaviour until dereferenced
允许尾后寻址的原因是为了便于编写遍历整个数组的循环,例如,while (*d++ = *s++);
.
数组的边界标记描述了一个半开范围,从(并包括)第一个元素开始,到(但不包括)最后一个元素结束:[beginning,end)
。