Адрес в качестве возвращаемого значения функции.

Когда функция возвращает адрес либо в виде переменной-указателя, либо в виде ссылки, пользователь получает некоторый адрес в памяти. Он может считать значение, находящееся по этому адресу, и, если тип указателя не объявлен как const, всегда может что-нибудь туда записать. Если функция возвращает адрес, то пользователь получает возможность читать и — в случае указателей, имеющих тип, отличный от const — обновлять локальные данные. Это важно для проектирования приложений.

Передача параметров функции по ссылке и по значению

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

При передаче параметров по значению они при выходе из функции не изменятся. Например, следующий фрагмент напечатет на экране 1 и 3:

... int func(int k) { k * = 2; return k; } void main(){ int z = 1, y = 3, k; k = func(z) + func(y); cout << z <<" " << y;...

При передаче же параметров по ссылке прив выходе из функции из значения могут измениться. Как, например, в следующем фрагменте:

... int func(int &k) { k* = 2; return k; } void main(){ int z = 1, y = 3, k; k = func(z) + func(y); cout<<z<<" "<<y;...

После его выполнения на экране напечатается 2 и 6.

Разница между двумя этими фрагментами весьма невелика - всего 1 символ амперсанда (&) в строке

...int func(int &k ){...

Еще один классический пример на эту тему - это функция, которая меняет значения своих параметров:

void func(int &n, int &m) { int tmp = n; n = m; m = tmp; }

После выполнения такой функции значения её параметров поменяются местами.

 

Использование встроенного отладчика.

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

Что происходит? При вызове функции ifirst_function() для переменной ilocal_to_first в стеке выделяется локальная область памяти, в которую записывается число 11. После этого функция ifirst_function() возвращает адрес этой локальной переменной (очень плохая новость!). Во второй строке функции mata() вызывается функция isecond_function(), которая в свою очередь выделяет локальную область памяти для переменной ilocal_to_second и записывает туда число 44. Почему же оператор printf печатает значение 44, хотя ему при вызове функции inrst_fiinction() был передан адрес переменной ilocaljojirsf?

Фактически происходит следующее. Когда при вызове функции ifirst_function() адрес временной локальной переменной ilocal_to_first был присвоен переменной pi, то этот адрес был сохранен, несмотря на завершение области действия ilocal_to_first. При вызове функции isecond_function(), ей также понадобилась локальная память. Поскольку переменной ilocal_to_first не стало, переменная ilocal_to_second получила ту же локальную .область, что и ее предшественница. Так как pi указывает на ту же занятую ячейку памяти, то становится понятным, почему при печати адресуемой ячейки появляется число 44. Следует быть чрезвычайно внимательным и стараться не возвращать адреса локальных переменных.

Использование ссылочного типа.

Подводя черту, можно выделить четыре основных причины использования ссылок C++:

· Ссылки упрощают восприятие программы, поскольку можно игнорировать детали процесса передачи параметра.

· Ссылки передают ответственность за передачу аргумента тому программисту, который пишет функцию, а не тому, который ею пользуется.

· Ссылки являются необходимой составной частью перегрузки операций.

· Ссылки используются при передаче функциям классов, при этом конструкторы и деструкторы не вызываются.

Ссылка представляет собой синоним имени, указанного при инициализации ссылки. Ссылку можно рассматривать как указатель, который всегда разыменовывается. Формат объявления ссылки:

тип & имя;

где тип — это тип величины, на которую указывает ссылка, & — оператор ссылки, означающий, что следующее за ним имя является именем переменной ссылочного типа, например:

int коl;
int& pal = kol; // ссылка pal - альтернативное имя для коl
const char& CR = '\n '; // ссылка на константу

Запомните следующие правила.

Ссылки применяются чаще всего в качестве параметров функций и типов возвращаемых функциями значений. Ссылки позволяют использовать в функциях переменные, передаваемые по адресу, без операции разадресации, что улучшает читаемость программы.

Ссылка, в отличие от указателя, не занимает дополнительного пространства в памяти и является просто другим именем величины. Операция над ссылкой приводит к изменению величины, на которую она ссылается.