Форум программистов, компьютерный форум CyberForum.ru

Ссылки и указатели - C++

Войти
Регистрация
Восстановить пароль
Другие темы раздела
C++ Построение UML http://www.cyberforum.ru/cpp-beginners/thread250365.html
Можно ли создать диаграмму зависимостей UML из существующего проекта VS 2005?
C++ написать программу если можно с объяснением!!!!!!!! http://www.cyberforum.ru/cpp-beginners/thread250357.html
C++ класс эллипс
ПОМОГИТЕ ПОЖАЛУЙСТА, начала изучать с++ столкнулась с такой вот задачей...... Определить класс эллипс, продемонстрировать использование класса. Члены класса: переменные, необходимые для того, чтобы иметь возможность пользоваться стандартными функциями рисования. Обязательны функции-члены класса: нарисовать, стереть, передвинуть эллипс, изменить радиусы эллипса. может у кого есть примеры для...
C++ Сложение, вычитание, умножение
Доброго времени суток! Помогите с задачей: Написать функцию, которая складывает, вычитает или умножает два целых числа и возвращает результат (операнды и знак операции +, – или * — параметры функции). Заранее Спасибо! PS есть наработки, но чёт не так, выдаёт ошибки: num1.cpp #include<iostream>
C++ Преобразование массива с использованием функции http://www.cyberforum.ru/cpp-beginners/thread250350.html
На языке С написать с помощью функции программу. Задание: Дана матрица А и вектор B. Из сумм элементов строк матрицы сформировать вектор C. Если минимальный элемент вектора C кратен минимальному элементу вектора B, то из положительных элементов матрицы А сформировать вектор D и упорядочить его по возрастанию. Иначе матрицу А упорядочить по возрастанию. Заранее благодарен...
C++ указатель(?) на массив ситуация: мне нужно, чтобы в main был определён двумерный массив, а класс мог бы его использовать: class map { unsigned short int *field; bool isVisiable; public: map(unsigned short int ???); void show (); void hide (); подробнее

Показать сообщение отдельно
Evg
Эксперт CАвтор FAQ
17462 / 5700 / 361
Регистрация: 30.03.2009
Сообщений: 15,636
Записей в блоге: 26
02.03.2011, 14:43     Ссылки и указатели
Цитата Сообщение от xKirillx Посмотреть сообщение
Добрый день.
Возможно было. В чем существенная разница между передачей данных в функцию по ссылке или указателю. В каких случаях вы бы что рекоммендовали. Заранее спасибо.
Глубоко в написанное не вчитывался, но ответ примерно такой.

Рассмотрим для начала простой случай, когда передаётся простая переменная. В точке вызова разницы нет никакой. Потому что в обоих случаях в функцию реально уходит адрес объекта и далее если в прототипе функции параметр описан как const указатель или const ссылка, то мы знаем, что внутри функции значение переменной не меняется, а если const'а нет - то полагаем, что внутри функции объект может поменяться. Внутри самой функции разница ровно такая же, как между указателем и ссылкой: над ссылкой нельзя проводить никакие операции и её нельзя изменять.

Какие из этого вытекают последствия (включая переход от простого случая к общему):

1. При наличии указателя мы не знаем, это указатель на объект или указатель на массив объектов (в языке Си между этим нет разницы). Т.е. имея на руках указатель мы можем работать с ним как с массивом. С сылкой этого сделать нельзя.

C
1
2
3
4
5
6
7
8
9
10
11
12
13
void func (int *p)
{
  /* Функция может сделать запись как в *p, так и к *(p+1), *(p+2) и т.п.
   * ровно как и в *(p-1), *(p-2) */
}
...
int x[10];
/* Передавая указатель на третий элемент массива, мы ничего не можем
 * сказать о дальнейшей судьбе всего массива. Т.е. не видя тела функции,
 * мы в данном месте не можем сказать, поменяется ли, к примеру, первый
 * или пятый элемент массива */
func (&x[3]);
...
C++
1
2
3
4
5
6
7
8
9
10
11
void (int &p)
{
  // Здесь уже обращения куда-то за границы одного int'а не возможны -
  // язык этого сделать не позволит
}
...
int x[10];
// Передавая третий элемент массива по ссылке, мы совершенно точно
// можем сказать, что первый и пятый элементы массива окажутся неизменёнными */
func (x[3]);
...
2. При наличии модификатора const перед ссылкой можно быть железно уверенным в том, что ни при каких обстоятельствах значение передаваемого аргумента не изменится. Если же мы работаем с указателем, то в результате ошибки программиста значение может измениться, что приводит к очень трудноуловимым ошибкам, которые с виду выглядят как ошибки компилятора, потому что компилятор доверился модификатору const. Реально это ошибка программиста

C
1
2
3
4
5
6
7
8
9
/* С виду функция выглядит так, что по указателю значения изменяться
 * не должны. Компилятор в точке вызова функции может заложиться на это свойство */
void (const int *p)
{
  /* Но средствами языка мы вполне можем обойти признак const и сделать
   * запись по указателю. */
  int *pp = (int*) p;
  *pp = 0;
}
3. Когда в функцию передаётся указатель, то в том числе может прийти и NULL (т.е. указатель, который никуда не указывает). Так же мы не застрахованы от того, что придёт кривой указатель при обращении к которому мы сломаемся в нашей функции, в то время как реально ошибка в точке вызова (или ещё выше).

C
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
void func (int *p)
{
  /* При реализации универсального интерфейса для порядку бы надо проверить,
   * что нам пришёл не NULL. При работе с ссылками такая ситуация невозможна */
  if (p == NULL)
    error (...);
 
  /* В данной ситуации нам остаётся только надеяться на то, что указатель корректен,
   * ибо если это не так, то программа сломается в этой точке */
  *p = 0;
}
...
int x;
/* Здесь мы подаём корректный указатель */
func (&x);
...
/* А здесь указатель оказался кривым (как следствие ошибки программиста).
 * Причём такую ситуацию отловить не возможно - нет для этого надёжных
 * технических способов. При любом обращении по такому указтелю программа
 * скорее всего свалится (за исключением случаев, когда выбранное число
 * окажется допустимым адресом) */
func ((int*) 0x12345678);
...
Добавлено через 3 минуты
До кучи пара ссылок
Сравнение указателей и ссылок.
Сравнение указателей и ссылок.
 
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2017, vBulletin Solutions, Inc.
Рейтинг@Mail.ru