Что означает * и & применительно к именам переменных? - PullRequest
13 голосов
/ 28 июля 2010

В C ++, в чем разница между:

 void func(MyType&); // declaration

 //...
 MyType * ptr;

 func(*ptr); // compiler doesnt give error

 func(ptr); // compiler gives error i thought & represents memory address so 
            // this statement should correct as ptr is only a pointer
            // or address of some real var.

Ответы [ 2 ]

23 голосов
/ 28 июля 2010

Унарный префиксный оператор & при применении к объекту дает адрес объекта: &obj.
Модификатор типа & применительно к переменной, которая должна быть объявлена, изменит тип переменной на ссылочный тип: int&.

То же самое относится к *: При применении в качестве унарного префиксного оператора к указателю, оно будет разыменованием указатель, приводящий к объекту, указанному: *ptr.
При использовании в качестве модификатора типа для переменной, которая должна быть объявлена, * изменитуказатель типа : int*.

Аналогичным образом модификатор типа [], примененный к объявленной переменной, изменит тип переменной на массив, тогда как бинарный инфиксный оператор [], примененный к объекту типа массива, будет обращаться к одному из подобъектов массива.


Бесполезно, что модификаторы типа применяются к объявленной переменной , а не к типу, с которым они объявлены.Например, этот

int *p, **pp, i, a[10], &r = i; 

определяет указатель int, указатель на указатель на int, ванильный int, массив 10 int и intссылка.(Последний сразу инициализируется, потому что вы не можете иметь неинициализированную ссылку.) Обратите внимание, что модификаторы типа синтаксически относятся к объявленной переменной , тип которой они изменяют, а не к объявленной переменнойтип.Тем не менее, модификаторы типов (* и &) изменяют тип переменной .
В следующем случае, однако, с предполагаемыми p, i и aпеременные, которые уже были объявлены

*pp = &i;
a[0] = i;

* и &, являются унарными префиксными операторами, разыменовывают pp и дают адрес i, тогда как [] возвращает первое int объект в массиве a.

Тот факт, что C и C ++ не заботятся о пробелах вокруг модификаторов типа и что это привело к различным лагерям, когда дело доходит доразмещение их на самом деле не делает вещи проще.
Некоторые люди помещают модификаторы типа близко к типу.Они утверждают, что он изменяет тип, и поэтому он должен идти туда:

int* ptr;

Недостатком является то, что это может сбивать с толку при объявлении нескольких объектов.Этот

int* a, b;

определяет a как указатель на int, но b как int.Вот почему некоторые люди предпочитают писать

int *ptr;
int *a, *b;

Я предлагаю просто никогда не объявлять несколько объектов в одном выражении.ИМО, что делает код легче для чтения.Кроме того, это дает вам возможность выбрать любую конвенцию.


Чтобы еще больше усложнить ситуацию, кроме модификаторов типа и унарных префиксных операторов & и *, существуют также бинарные инфиксные операторы & и *, что означает «побитовое И» и «умножение».И чтобы добавить оскорбление раны, в C ++ вы можете перегрузить как унарный префикс , так и двоичный инфикс варианты этих операторов (и двоичный инфикс []) для пользовательских типов и полностью свободны в отношении их семантики.

4 голосов
/ 28 июля 2010

MyType & представляет собой / reference /, совершенно другого зверя по отношению к указателям.Если ваш прототип функции был

func (MyType);

вы бы работали с копией аргумента внутри функции.С

func (MyType &);

вы работаете с самим объектом (т. Е. Одним и тем же объектом как в вызывающей, так и в вызываемой области действия).В данном случае это похоже на работу с указателем, но с использованием того же синтаксиса «точка», что и для объектов.

Конечно, это поверхностное и упрощенное объяснение.Для того, чтобы я почувствовал полное усердие, схватившись за глубокие дзен-указатели, ссылки и остальную часть орды, потребовались годы.

...