Почему ++ (* p) меняет значение указателя? - PullRequest
9 голосов
/ 13 июля 2020

Если у меня есть этот код:

int A[5] = { 2, 1, 3, 55 };
int *p = A;
cout << ++(*p);

, результат будет 3, а значение первой позиции A тоже будет 3, почему?

I значит, по иерархии операторов () более иерархичен, чем ++, тогда нам нужно сначала выполнить *p:

++(*p) => ++(2) => 3 

с любым изменением в A vector?

Ответы [ 3 ]

19 голосов
/ 13 июля 2020

*p - это не просто «2», это lvalue , то есть эта «2» имеет четко определенное местоположение. Значение в этом месте изменяется оператором ++ - по определению оператора ++.

Если вы не хотите изменять значение, используйте вместо него + 1: *p + 1.

В C / C ++ lvalue - это значение с определенной ячейкой в ​​памяти. Это значение можно изменить - присваиванием, увеличивая, уменьшая. Например,

int x = 0;
x = 1; // ok, x is an lvalue, assignment changes the value from 0 to 1

int *p = &x;
*p = 2; // ok, *p is an lvalue, assignment changes the value from 1 to 2

Напротив, rvalue - это значение без определенного местоположения - например, результат операции arithmeti c. Это значение не может быть присвоено, увеличено или уменьшено (это не означает, что его нельзя использовать в более крупном выражении).

Например,

int x = 0, y = 1;
(x + y) = 3; // compilation error, (x + y) is an rvalue

2++; // compilation error, 2 is an rvalue

Вот довольно простая статья, объясняющая lvalues ​​/ rvalues: https://eli.thegreenplace.net/2011/12/15/understanding-lvalues-and-rvalues-in-c-and-c

5 голосов
/ 13 июля 2020

++(*p) совпадает с ++p[0] и ++A[0] Все изменяют первый элемент массива.

Почему ++ (* p) изменяет значение указателя

Это не так. Значение указателя хранится в p. Это называется «адрес» или «ссылка». Не меняется.

0 голосов
/ 18 июля 2020

Стоит отметить чрезмерное использование '*' в C ++, которое обычно сбивает с толку новичков.

Здесь:

int *p = A;

'*' означает, что вы объявляете p как переменную, которая может хранить адрес памяти (указатель) и присвоение адреса первой позиции A (это то же самое, что и & (A [0])).

Здесь:

++(*p)

' * 'означает, что вы просматриваете содержимое' p '(ссылка на адрес' p ', который совпадает с адресом' A [0] '). Затем '++' увеличивает значение, которое отражает оба.

Просто для подтверждения, после этого присвоения (int * p = A;) выведите значения 'p', 'A' и '& A [0 ] '.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...