Указатели и константы

Fd9c 0.000000

Fd9c 123

Операция приведения типов.

ОПЕРАЦИИ С УКАЗАТЕЛЯМИ

С указателями можно выполнять следующие операции:

1) разыменование (*);

2) присваивание;

3) арифметические операции (сложение с константой, вычитание, инкремент ++, декремент --);

4) сравнение;

5) приведение типов.

Операция разыменования.

 

Пример 50

int a; //переменная типа int

int *pa=new int; //указатель и выделение памяти под динамическую переменную

*pa=10; //присвоили значение динамической переменной, на которую указывает указатель

a=*pa; //присвоили значение переменной а

 

Присваивать значение указателям-константам запрещено.

 

На одну и ту же область памяти могут ссылаться указатели разного типа. Если применить к ним операцию разыменования, то получатся разные результаты.

 

Пример 51

int a=123;

int *pi=&a;

char *pc=(char*)&a;

float *pf=(float*)&a;

printf(«\n%x\t%i»,pi,*pi);

printf(«\n%x\t%c»,pc,*pc);

printf(«\n%x\t%f»,pf,*pf);

При выполнении программы, представленной в примере 51, получатся следующие результаты:

66fd9c {

Т.е. адрес у трех указателей один и тот же, но при разыменовании получаются разные значения в зависимости от типа указателя.

Арифметические операции применимы только к указателям одного типа.

1. Инкремент увеличивает значение указателя на величину sizeof(тип).

 

Пример 52

char *pc;

int *pi;

float *pf;

...

pc++; //значение увеличится на 1

pi++;//значение увеличится на 4

pf++; //значение увеличится на 4

 

2. Декремент уменьшает значение указателя на величину sizeof(тип).

3. Разность двух указателей – это разность их значений, деленная на размер типа в байтах.

4. Суммирование двух указателей не допускается. Можно суммировать указатель и константу.

 

Пример 54

Если p = &v[3]; //указатель p содержит адрес 4-го элемента массива v

то p = p + 2; //указатель p содержит адрес 6-го элемента массива v

 

При записи выражений с указателями требуется обращать внимание на приоритеты операций.

Например:

 

char *p = "asdf"; // обычный указатель

const char *pc ="ghjk" ; // указатель на константу

pc[3] = 'a'; // ошибка, pc указывает на константу

pc = p; // нормально

 

Чтобы объявить как константу сам указатель, а не указываемый объект, нужно использовать оператор объявления *const, а не просто const. Кроме того, оператор *const нужно ставить после типа объекта.

Например:

 

char *p = "asdf"; // обычный указатель

char *const сp ="ghjk" ; // указатель - константа

сp[3] = 'a'; // нормально

сp = p; // ошибка, указатель сp - константа

 

Чтобы сделать константами и указатель, и объект, надо оба объявить как const, например:

 

char *p = "asdf"; // обычный указатель

const char *const cpc = "asdf"; // указатель-константа и объект -константа

cpc[3] = 'a'; // ошибка

cpc = p; // ошибка

 

 

Указателю на константу можно присвоить адрес переменной, т. к. это не принесет вреда. Однако адрес константы нельзя присвоить указателю без спецификатора const, иначе можно изменить значение объекта. Например:

 

int a = 1;

const int c = 2;

const int *p1 = &c; // нормально

const int *p2 = &a; // нормально

int *p3 = &c; // ошибка, так как возможна следующая инструкция,

*p3 = 7; // меняющая значение c