3

unsequenced modification and access to 'ptr'

why can't I ever use the ++ incrementer in a loop? It only ever works for me in the loop conditions. I changed the code to *ptr = *ptr + 1; and it works fine. This has happened in a few different situations.

6
*ptr = *ptr + 1;

and

*ptr = *ptr++;

are different in the since that the first dereferences the location pointed to by ptr adds 1 to the value in there and stores the result back in that location.

the second dereferences the location pointed to by ptr, stores the value in there in the same location (which is actually kinda pointless but that's not the point) and increments ptr itself.

What is the error all about?

of course it's not about the loop. it's about something called sequence points. per the article:

A sequence point defines any point in a computer program's execution at which it is guaranteed that all side effects of previous evaluations will have been performed, and no side effects from subsequent evaluations have yet been performed.

in a more casual way, this just means that you have something called a sequence point that refers to a point in a program's execution where an operation and all its side effects (if any) are completely performed.

the expression *ptr++ has a side effect — it increments ptr. quoting the standard (§6.5):

Between the previous and next sequence point an object shall have its stored value modified at most once by the evaluation of an expression. Furthermore, the prior value shall be read only to determine the value to be stored.

this just means that you shouldn't modify the value of a variable twice between two sequence points and if you're ever going to access and modify the value of a variable between two sequence points, then the access(es) should be directly involved in the computation of the value that will end up being stored in that variable.

in the expression *ptr = *ptr++;, ptr is accessed and modified (incremented) between two sequence points but it is not accessed for the purpose of computing the value that will end up being stored in ptr (it is obviously accessed to be dereferenced). so the behavior of such operation is undefined.

As a simpler example (doesn't involve pointers):

i = i + 1; // defined

because even though i is accessed and modified between two sequence points, the access was for the purpose of determining the value to be stored in i.

while

j = i + i++; // undefined

because i is accessed and modified between two sequence points and when it is accessed, it has nothing to do with determining the value to be stored in i after it is modified.

What should you do?

I don't think you wanted to increment ptr. rather, you probably wanted to increment the value pointed to by ptr and to do that it would be sufficient to do something like:

(*ptr)++;
2

Just in case there's unclarity about the increment operator(s).

In C, the increment operators actually increment the value without the need to assign it to anything. The original value is incremented even though the old value (or the new one, in case of the prefix increment operator, ++i) is returned.

So if we have

int i = 0;
i++;   // evaluates to 0, actual value in i is 1

or if we have

int i = 0;
++i;   // evaluates to 1, actual value in i is 1

we don't actually have to assign it to a new variable or to i, i's value has already been incremented.

| improve this answer | |
0

Andrej's example is essentially accurate, but confusing and incomplete, particularly about what it 'returns' and, more imoportantly, to what. Essentially, in the example, there's nothing to return anything to, so the return value is abandoned. I'll refine it here a bit to make more sense.

int i=0;
int j;
int k;

j = i++;  // i starts as 0, 0 is assigned to j and then i is incremented to 1

i++;      // i is simply incremented by 1 to a value of 2.

k = ++i   // i starts at 2 from previous line, is incremented by 1 to become 3,
          // and then k is assigned the value of 3

In summary, if the ++ operator preceded the variable name, the increment operation is done before the line of code is evaluated. If the ++ operator follows, then the line of code is evaluated first, and then the variable is incremented. The same rules apply for the -- decrement operator.

If one of these answers satisfies your question, please accept that answer to remove this question from the unanswered pool. Let's keep up on forum maintenance. :-)

| improve this answer | |

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .