阅读背景:

在c程序中使用++ * p ++会产生分段错误

来源:互联网 

Code:

#include <stdio.h>

int main(int argc, char const *argv[])
{
    char *p1="khan",*p2;
    p2 = p1;

    while ( *p1 != '

Code:

#include <stdio.h>

int main(int argc, char const *argv[])
{
    char *p1="khan",*p2;
    p2 = p1;

    while ( *p1 != '\0')
    {
        // printf("I am in while.\n");
        ++*p1++;
        // printf("I am after ++*p1++.\n");

        printf("%c\n",*p1 );
    }
    printf("%s %s\n", p1,p2);
}

The compilation of above code gives unexpected results:

上面代码的编译给出了意想不到的结果:

Segmentation fault (core dumped)

分段故障(核心转储)

Here is what I am expecting:

这是我所期待的:

++*p1++;
  1. Post ++ has higher precedance: p1 = p1 + 1.
  2. Post ++具有更高的先验:p1 = p1 + 1。

  3. Now, p1 will point to the p1 -> h.
  4. 现在,p1将指向p1 - > h。

  5. We have two operators here ++*, * has higher precedance. So *p1 will be increased and we have value, *p1 = i;
  6. 我们这里有两个运算符++ *,*具有更高的先验。所以* p1会增加,我们有价值,* p1 = i;

Now, I should get "ki.." in p1. But, I am unable to iterate only once in while loop.

现在,我应该在p1中获得“ki ..”。但是,我无法在while循环中只迭代一次。

 printf("I am in while.\n");
   ++*p1++; //getting error here.
 printf("I am after ++*p1++.\n"); //this line is never called

3 个解决方案

#1


2  

The expression

++*p1++

is parsed as

被解析为

(++ (* (p1 ++) ) )

and evaluated as follows:

并评估如下:

  1. p1++ is evaluated; the result of the expression is the value of p1 before the increment;
  2. p1 ++被评估;表达式的结果是增量前p1的值;

  3. the result of 1 is dereferenced
  4. 1的结果被解除引用

  5. the result of 2 is incremented
  6. 2的结果递增

  7. Somewhere between the end of 1 and now, p1 is advanced to point to the next element.
  8. 在1结束和现在之间的某处,p1被提前指向下一个元素。

You're getting the segfault because you're attempting to alter the contents of a string literal, which is not allowed. Change your code to something like

你得到了段错误,因为你试图改变字符串文字的内容,这是不允许的。将代码更改为类似的内容

char str[] = "khan";
char *p1 = str;

and it should work. Note that your output will be "libo", not "kibo".

它应该工作。请注意,您的输出将是“libo”,而不是“kibo”。

#2


2  

++*p1++;

is equal to

等于

(++*(p1++));

which attempts to modify the string literal. Problem is:
Modifying string literals is undefined behavior.

它试图修改字符串文字。问题是:修改字符串文字是未定义的行为。

Therefore p1 should be a const char*, which is also strictly enforced in C++.

因此p1应该是一个const char *,它也在C ++中严格执行。

Try

char str[] = "khan";
char* p1 = str;

for example. This will store the string on the stack and not in some read-only section.

例如。这会将字符串存储在堆栈中,而不是存储在某些只读部分中。

#3


-1  

Actually it is undefined behaviour.

实际上它是未定义的行为。

++*p++

We would have no way of knowing which order the two increments would happen in, and in fact the compiler wouldn't have any idea either. We could not argue that since post has higher precedence than pre, and since * and ++ associates from left to right, you are thinking that it would happen like this:

我们无法知道两个增量会发生在哪个顺序,实际上编译器也不会有任何想法。我们不能说因为post的优先级高于pre,并且因为*和++从左到右关联,所以你认为它会像这样发生:

p1++;
++(*p1);

but it could happen the other way ++(*p1) followed by p1++. The string could be modified and the string would become

但它可能发生另一种方式++(* p1)后跟p1 ++。字符串可以修改,字符串将成为

"libo"

because ++ just says that the increment happens later, not that it happens immediately.

因为++只是说增量发生在后面,而不是它立即发生。


') { // printf("I am in while.\n"); ++*p1++; // printf("I am after ++*p1++.\n"); printf("%c\n",*p1 ); } printf("%s %s\n", p1,p2); } #include <stdio.h> int main(int argc,



你的当前访问异常,请进行认证后继续阅读剩余内容。

分享到: