Программирование >>  Аргументация конструирования 

1 ... 23 24 25 [ 26 ] 27 28 29 ... 108


расположении переменных в памяти

tinclude <3tdio,h> ttinclude <iostream.h>

indnt intArgc, char* pszArgs[]) {

int ir.l;

int n;

long 1;

float f;

double d; int ш2;

ЕЫВОД даатеричном виде cout.setf (ios: :hex);

выводить адреса переменных

no очереди, чтобы показать размер каждой переменной

J- = Ох (long) £ml << ; \n

&n = Ox (longl&n < =; \n

5l = Ox (long)SI <<; \n

Sf = Ox (long) uf < v \n

id = Ox (long)id < = \n

cout << cout

<< << << <<

Ox (long) £,m2 <<c \n

return 0 ,


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

Сравнив расположение переменных, можно заключить, что п занимает четыре байта, 1 также занимает четыре и т.д. (в соответствии с приведенной таблицей).

iJ* И GNU C + + , и Visual C + + выделяют одинаковое количество памяти под переменные одного типа.

использование/А:аза/1е.4еи

Переменная-указатель содержит адрес, обычно это адрес другой В табл. 8.2 приведены основные операторы для работы с указателями.

Таблица 8.2. Операторы для работы суказателями

переменной.

ОПЕРАТОР

НАЗНАЧЕНИЕ

ньй) Получить адрес переменной

* (унарный) Операция разыменования - возвращает переменную, на которую указы-

вает указатель (в выражении).

Указатель на даннтй тип (в объявлении)

Пример работы с операторами приведен в следующем листинге:

Глава 8. Первое знакомство с указателями в C++



void fn ()

in iiitVar; iriL* pintVar;

pi ntvar Var; pmtVar указывает на intVar

*p:ntVar = 10; сохраичет 10 Б переменой типа int

} по адресу, находящемуся в pintVar

Функция fn () начинается с объявления переменной intVar; в следующей строке объявляется pir.tVar - указатель на неременную тина int.

Указатели объявляются как обычные переменнь[е, но в объявление добавляется унарный оператор *, который может быть использован совместно с именем любого тина. В данной строке этот символ иснользуется вместе с именем фундаментального тина int. Однако этот оператор может использоваться для добавления к любому имени переменной типа.

При написании программ желательно придерживаться соглашений об именах, в соответствии с которыми первый символ в названии переменной указывает на ее тип. Например, можно использовать для int, d для double и т.д. С учетом этого соглашения имена указателей далее в книге будут начинаться с буквы р.

Унарный оператор & в выражении означает взять адрес переменной . Таким образом, в первой строке приведенного кода находится команда сохранения адреса переменной intVar в переменной pintVar.

Представим себе, что функция fn <} начинается с адреса 0x100, переменная расположена по адресу 0x102, а указатель pintVar - 0x106 (такое расположение намного проще результатов работы программы Layout; на самом деле вряд ли переменные будут храниться в памяти именно в таком порядке).

Первая команда программы сохраняет значение в указателе

pintVar. Вторая строка отвечает за присвоение значения 10 переменной, хранящейся но адресу, который содержится в указателе pintVar (в нем находится число 0x102,

т.е. адрес переменной intVar).

Сравнение указателей и почтовых адресов

Указатели похожи на адреса домов. Ваш дом имеет уникальный адрес, и каждый байт в памяти компьютера тоже имеет уникальный адрес. Почтовый адрес содержит

набор цифр и букв. Например, он может выглядеть так: 123 Main Street (конечно же,

это не мой адрес! Я не люблю нашествий поклонников, если только они не женского пола). Адрес переменной в памяти содержит только цифры (например, 123456).

Можно хранить диван в доме по адресу 123 Main Street, и точно так же можно хранить число в памяти по адресу 0x123456. Можно взять лист бумаги и написать на

нем адрес - 123 Main Street. Теперь диван хранится в доме, который находится по адресу, написанному на листке бумаги. Так работают сотрудники службы доставки: они доставляют диваны по адресу, который указан в бланке заказа, независимо от того, какой именно адрес записан в бланке (я ни в коем случае не смеюсь над работ-пиками службы доставки - просто это самый удобный способ объяснить указатели). Использовав синтаксис С++, это можно записать так:

House myHouse; House houseZVddress; houseAddress = &rr.yHouse; houseAddress = coucii;

Эта запись обозначает следующее: является домом, a houseAddress -

адресом дома. Надо записать адрес дома myHouse в указатель houseAddress и доставить диван по адресу, который находится в указателе houseAddress.



Теперь используем вместо дома переменную типа int:

int mylnt; int* intAddress; intAddress = Smylnt; intAddress = 10;

Аналогично предыдущей записи, это поясняется так int - переменная типа int. Слелует сохранить адрес raylnt в указателе intAddress и записать 10 в переменную, которая находится по адресу, указанному в intAddress.

Использование разных типов указателей

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

int* pintVar = SintVar; обе части этого присвоения

имеют тип *int Аналогично pintVar еет тип int*, a *pintVar - тип int: *pintVar =10 обе части этого присвоения

еют int

Тип переменной, на которую указывает pintVar, - int. Это эквивалентно тому,

что если nouseAddress ЯВЛЯСТСЯ адрССОМ ДОМа, то, как ни странно, houseAddress

указывает дом.

Указатели на переменные других типов объявляются точно так же:

double dDubleVar

double* odoubleVar = sdoubleVar *pdoubleVar =10.0

В компьютере класса Pentium размер указателя равен четырем байтам, независимо от того, на переменную какого типа он указывает14.

Очень важно следить за соответствием типов указателей. Представьте, что может произойти, если компилятор в точности выполнит такой набор команд:

int nl;

int* pintVar;

pintVar = &nl; *pintVar = 100.0;

Последняя строка требует, чтобы адресу, выделенному под переменную размером в четыре байта, было записано значение, имеющее размер восемь байтов. На самом деле ничего страшного не произойдет, поскольку в этом случае компилятор приведет 100.0 к типу int перед тем, как выполнить присвоение.

Привести переменную одного типа к другому явным образом можно так:

int iVar;

double dVar - 10.0;

iVar - (int)dVar;

Так же можно привести и указатель одного типа к другому:

int* piVar;

double dVar = 10.0;

double* pdVar;

piVar = (lnt*)pdVar;

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



1 ... 23 24 25 [ 26 ] 27 28 29 ... 108

© 2006 - 2024 pmbk.ru. Генерация страницы: 0
При копировании материалов приветствуются ссылки.
Яндекс.Метрика