1. pointer increment

I know incrementing a pointer in this fashion: ptr += 2, involves an addition and multiplication ( 2 * sizeof ptr), whereas doing ptr++ only requires addition.

My assumption was that ptr += 1 would be equivalent to ptr++, however, recently I discovered that ptr += x, where x is always 1 || 0, resets ptr to its starting address when x == 0. This makes me question my original assumption that only addition is involved.

Could it be that because I am using a variable, the compiler treats the code just as if x could contain any other number, which I guess technically it could, and it reverts to my former example or is multiplication always used when employing anything other that postfix increment?

Is there any way to circumvent this, i.e increase a pointer in a manner that is equivalent, instruction wise, to ptr++ while retaining the flexibility of using a variable?

I guess I could pre-compute: size = sizeof ptr and then:
while (x < size)
ptr++;

but I'm not sure if that would be any faster, in fact it could be a lot slower.

And while we are at it, is there a difference, instruction wise, between ptr[x] and (ptr + x).

While typing this, I just realized I could probably get most of my answers by looking at the assembly code generated for the different versions of my code, but I've already written all of this and would still like to get your input.

Thank you guys!

2. > I know incrementing a pointer in this fashion: ptr += 2, involves an addition and multiplication (2 + 2 * sizeof ptr), whereas doing ptr++ only requires addition.
This is wrong.

There is ALWAYS an implied multiplication when incrementing pointers, since it always involves the size of the type it points to. Where the increment is a constant, the multiplication happens in the compiler, not at runtime.

> however, recently I discovered that ptr += x, where x is always 1 || 0, resets ptr to its starting address when x == 0. This makes me question my original assumption that only addition is involved.
Post actual code demonstrating this, along with saying which OS/Compiler you're using.
If x is 0, then multiplying it by anything will still get you 0, and ptr will just remain at the value it previously had.

> I guess I could pre-compute: size = sizeof ptr and then:
Now you're not making an sense at all.
Voodoo programming - Wikipedia

It seems to me there is something broken previously in your code, and now you're just trying to rationalise weird behaviour.

> And while we are at it, is there a difference, instruction wise, between ptr[x] and (ptr + x).
I suppose it's always possible that a compiler might do something different, but the end result will be functionally the same.

3. There is ALWAYS an implied multiplication when incrementing pointers, since it always involves the size of the type it points to. Where the increment is a constant, the multiplication happens in the compiler, not at runtime.
I see. That is an interesting distinction and it also answers my question. Good to know. Incrementing a pointer results in no multiplication *at runtime*, when using a constant, but multiplication is always needed. I guess it is safe to assume the compiler treats ptr++ as a constant too, correct? So it ends up avoiding the runtime multiplication penalty. So technically, *at runtime*, ptr++ requires no multiplication. That is what I had in mind when writing my statement above -though it was not completely accurate or if we are being pedantic, simply not accurate at all- and I appreciate the clarification.

Now you're not making an sense at all.
Well, I am interested in eliminating the multiplication penalty in a particular loop in my code; Why? simply for performance reasons. Technically if I increase the pointer as I show in that little loop in my comment above, I'm forfeiting the mandatory sizeof operation every time I increase the pointer (assuming my assertion above that ptr++ is indeed treated as a constant); but the resulting code will probably be slower than doing a regular ptr += x.

I hope I'm making sense now. If not, I'm blaming my lack of sleep. Again.

As for the pointer being reset. I have to clarify, in this case I was referring to a char **ptr.
Dereferencing ptr like this (*prt) += x, leads to *ptr being reset to it's original address when x = 0. I didn't know this. The same way I didn't know that increasing the copy of a dereferenced pointer would also increase the content of the original poitner. i.e
Code:
```char **ptr = //assume something valid;
char **ptr2 = ptr;

(*ptr2)++;
*ptr == *ptr2; //True```
If this not normal, I am more than happy to provide the code, and platform.

4. Originally Posted by Dren
Well, I am interested in eliminating the multiplication penalty in a particular loop in my code; Why? simply for performance reasons. Technically if I increase the pointer as I show in that little loop in my comment above, I'm forfeiting the mandatory sizeof operation every time I increase the pointer (assuming my assertion above that ptr++ is indeed treated as a constant); but the resulting code will probably be slower than doing a regular ptr += x.
The multiplication implied by pointer arithmetic is computed at compile time, hence it will have no effect on runtime performance.

Originally Posted by Dren
As for the pointer being reset. I have to clarify, in this case I was referring to a char **ptr.
Dereferencing ptr like this (*prt) += x, leads to *ptr being reset to it's original address when x = 0. I didn't know this. The same way I didn't know that increasing the copy of a dereferenced pointer would also increase the content of the original poitner. i.e
No, no such thing happens. There is no "reset". You have merely misinterpreted the code.

What you have here is this:
ptr2 is a copy of ptr, therefore *ptr and *ptr2 refer to the same object.
You increment *ptr2.
You observed that *ptr == *ptr2 is true. But of course! They are the same object!

5. Well (*ptr++)++ is really going to bake your noodle then

There's a big difference between incrementing the pointer, and incrementing what it points at.

> Why? simply for performance reasons.
Consider that compilers have 1000's of man-years of experience distilled into their code generators, any attempt you make to try and get the better of them will backfire.

40 years ago, when compilers were little more than dumb literal translation of code into assembler, you might have won occasionally.

But a modern optimising compiler is a completely different beast.

For example, all those sizeof's you're worrying about are frequently going to get reduced into shift-and-add rather than multiply-and-add.

Focus on writing clear and correct code, and forget about trying to micro-manage each step.