How does a unary padding on C pointers work?

I know that a unary operator ++ adds one to a number. However, I find that if I do this with an int pointer, it increases by 4 (the size of an int int in my system). Why is he doing this? For example, the following code:

int main(void) { int *a = malloc(5 * sizeof(int)); a[0] = 42; a[1] = 42; a[2] = 42; a[3] = 42; a[4] = 42; printf("%p\n", a); printf("%p\n", ++a); printf("%p\n", ++a); return 0; } 

will return three numbers with a difference of 4 between each.

+4
source share
9 answers

This is just C method - full explanation in the specification, Section 6.5.6 Additive operators , clause 8:

When an expression that has an integer type is added or subtracted from the pointer, the result is the type of the operand of the pointer. If the pointer operand points to an element of the array object, and the array is large enough, the result indicates the offset of the element from the original element, so that the difference between the indices of the resulting and initial elements of the array is an integer expression. In other words, if the expression P points to the ith element of the array object, the expressions (P)+N (equivalent to N+(P) ) and (P)-N (where N has the value n) indicates respectively i + n -th and i- n -th elements of the array, if they exist. Moreover, if the expression P points to the last element of the array object, the expression (P)+1 indicates one after the last element of the array object, and if the expression Q indicates one after the last element of the array object, the expression (Q)-1 indicates the last element of the object array. If both pointer operands and the result point to elements of the same array object or one after the last element of the array object, the evaluation should not lead to overflow; otherwise, the behavior is undefined. If the result indicates one after the last element of the array object, it should not be used as the operand of the unary operator * , which is evaluated.

To associate this with your use of the ++ prefix, you also need to read Section 6.5.3.1 Prefix increment and decrement operators , clause 2:

The prefix ++ operand value is incremented. The result is the new value of the operand after the increment. The expression ++E equivalent (E+=1) .

As well as Section 6.5.16.2 Compound assignment , clause 3:

A compound assignment of the form E1 op = E2 differs from a simple assignment expression E1 = E1 op (E2) only in that the lvalue E1 is evaluated only once.

+6
source

Increases pointer location by int size, declared pointer type.

Remember that int * is just a pointer to a place in memory where you say that "int" is stored. When you are a ++ pointer, it shifts it in one place (by type size), in which case it will make your value "4" higher, since sizeof(int)==4 .

+3
source

The reason for this is the statement of the following statement:

 *(ptr + n) == ptr[n] 

They can be used interchangeably.

+2
source

In pointer arithmetic, adding one to the pointer will add the size of the type it points to.

so for this:

 TYPE * p; 

Adding to p will actually increase by sizeof(TYPE) . In this case, the size of int is 4.

See this related question.

+1
source

Since in "C" the arithmetic of the pointer is always scaled to the size of the object pointed to. If you think about it a little, this will be the "right thing."

+1
source

He does this so that you do not start accessing an integer in the middle.

+1
source

Because the pointer is not a reference;). It is not a value, it is just an address in memory. When you check the value of a pointer, it will be a number, possibly large and not related to the actual value that is stored in this memory location. Say printf("%p\n", a); prints "2,000,000" - this means that your pointer points to the 2,000,000th byte in your machine memory. He almost does not realize what value he stores there.

Now the pointer knows what type it points to. An integer in your case. Since the integer is 4 bytes long, when you want to go to the next "cell" that the pointer points to, it should be 2000004. This is more than 1 integer further, so a++ makes sense.

BTW, if you want to get 42 (from your example), print the value indicated by: printf("%d\n", *a);

Hope this makes sense;)

0
source

This is simple because when it comes to the pointer, in your case an integer pointer, unary increment means INCREMENT THE MEMORY LOCATION by ONE UNIT, where ONE UNIT = SIZE OF INTEGER.

This integer size depends on compilation with the compiler, for 32-bit and 16-bit - 4 bytes, and for 64-bit compiler - 8 bytes.

Try to make the same program with a characteristic type of characters, it will give a difference of 1 byte, since a character takes 1 byte.

In short, the difference is 4, that you are faced with a difference from SIZE OF ONE INTEGER in memory.

Hope this helps, if I didn’t do it, I will be happy to help, just let me know.

0
source

"Why is he doing this?" Why do you expect him to do anything else? The increment of a point causes it to point to the next element of the type that it points to.

0
source

Source: https://habr.com/ru/post/1339764/


All Articles