1

有人可以解释为什么

int main(int argc, const char * argv[]) {
  while (* argv) 
    puts(* argv++);
  return 0 ;
}

是合法的,并且

int main(int argc, const char * argv[]) {
  argv += argc - 1;
  while (* argv) 
    puts(* argv--);
  return 0 ;
}

不是吗?在这两种情况下,while 循环内的 'crement 都将指向 argv 的边界之外。为什么指向一个虚构的较高索引而不是一个虚构的较低索引是合法的?

此致。

4

4 回答 4

1

因为C标准说你可以形成一个指向数组末尾的指针,它仍然会正确地与指向数组的指针进行比较(尽管你不能取消引用它)。

对于指向数组开头之前的地址的指针,该标准没有说任何类似的东西——即使形成这样的指针也会产生未定义的行为。

于 2013-04-15T19:18:48.737 回答
0

循环语义和半开区间。遍历指针指向的对象的数组或列表的惯用方法是:

for (T *p = array; p < array + count; p++)

在这里,p最终超出范围(减一,指向数组末尾之后的一),因此(不仅在概念上)要求它不要调用未定义的行为(标准实际上强加了这个要求)。

于 2013-04-15T19:18:46.700 回答
0

The standard forces argv[argc] to be equal to NULL, so dereferencing argv when it's been incremented argc times is legal.

On the other hand nothing is defined about the address preceding argv, so argv - 1 could be anything.

Note that argv is the only array of strings guaranteed to behave this way, as far as I know.

From the standard:

5.1.2.2.1 Program Startup

If they are declared, the parameters to the main function shall obey the following costraints:

argv[argc] shall be a null pointer

于 2013-04-15T19:28:33.543 回答
0

argv++或者++argv因为它是 const 指针。

如果您采用简单的数组char* arr[10]并尝试arr++它会出错

于 2013-08-20T20:40:10.307 回答