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

Ступор в возврате указателей и ссылок - C++

Восстановить пароль Регистрация
 
Unifan
 Аватар для Unifan
0 / 0 / 0
Регистрация: 11.08.2014
Сообщений: 40
15.08.2014, 17:22     Ступор в возврате указателей и ссылок #1
Изучаю С++ базовый курс от Шилтда, все проходил на твердую четверку, и на предпоследней теме про системы ввода-вывода абсолютно запоролся про указатели и ссылки. И дело то не в том, что я не понимаю как использовать их (т.е. в качестве параметров функций и т.х), а в том, что я не понимаю, как работает функция, вовращающая их тип...
Товарищи программисты, прошу вас раз и навсегда объяснить мне в подробностях про функции, возвращающие указатели и ссылки.

Заранее спасибо.
После регистрации реклама в сообщениях будет скрыта и будут доступны все возможности форума.
St1f1er
2 / 2 / 0
Регистрация: 08.08.2014
Сообщений: 14
15.08.2014, 17:53     Ступор в возврате указателей и ссылок #2
Судя по вопросу нужно =) заново штудировать. И еще почитать про память чтоб понимать указатели. Обычная функция просто вернет указатель ( адресс в памяти)
Unifan
 Аватар для Unifan
0 / 0 / 0
Регистрация: 11.08.2014
Сообщений: 40
15.08.2014, 18:03  [ТС]     Ступор в возврате указателей и ссылок #3
Так на то это и ступор, ибо про указатели, да ссылки я знаю практически все ( то что в книге преполается ) и действие этих указателей, ровно также как и ссылок понимаю. Проблема в том, что до меня не доходит то, что именно возвращает в вызываемый код, посредством предложения return.
C++
1
2
3
4
5
6
7
8
return *a; // возвращает значение по адресу
return a; // возвращает адрес 
//-------------------------
int &func(//...) {
 //...
return &a; // что делает?
return a; // что делает?
}
Добавлено через 3 минуты
Пока сообщение писал, нервный ступор, заставлявший грызть ногти, начал утихать. Про указатели вроде бы сам понял, но про ссылки, особенно после таких предложений ( ostream &operator<<(ostream &stream_left, class_name obj_right ) понять не могу. То есть зачем поток должен возвращаться как ссылка? На что это вообще ссылка указывает?
A_Kamolins
 Аватар для A_Kamolins
4 / 4 / 4
Регистрация: 15.08.2014
Сообщений: 30
15.08.2014, 18:20     Ступор в возврате указателей и ссылок #4
Сообщение было отмечено автором темы, экспертом или модератором как ответ
Если a - это обычная переменная, то:
return &a; //Возвращает адрес этой переменной
return a; //Возвращает значение переменной

Если работаем с указателем
return *a; //Разыменование, т.е. возвращается значение, которое находится по адресу,который содержит указатель
return a; //Возвращается адрес, который содержит указатель

Добавлено через 3 минуты
По идее - тебе надо просто вникнуть в 2 вещи. Указатель, это как обычная переменная, которая может содержать адреса ячеек. Когда мы объявляем указатель, то перед его названием ставим звездочку.

C++
1
2
3
4
5
int *a; //объявляем указатель a, который может содержать адреса целочисленных переменных
int b = 30; //обычная целочисленная переменная, которой присвоили значение 30
a = &b; // &b - взятие адреса и присваивание его указателю a
 
cout << *a; //разыменовываем указатель, тоесть теперь он должен вывести то, что находится по адресу &b
Lynatik001
 Аватар для Lynatik001
34 / 28 / 2
Регистрация: 28.09.2012
Сообщений: 560
15.08.2014, 18:24     Ступор в возврате указателей и ссылок #5
Допустим у нас есть обьект окно проекта. Его нужно передать в функцию что бы она вывела через етот обьект на окно что-то. Но передавая не как ссылку мы создаем временный аналог окна который только существовал бы в функции, и при выходе с ее окно то бы уничтожалось. А то окно где надо было нарисовать- нечего бы не было. А когда мы передаем ссылку то мы передаем все то окно в котором надо нарисовать то-то, и оно изменяется.
тоже самое и указатель с ссылкой. Указатель передает только значение- не поменяется переменная если менять ее в функции, а с ссылкой поменяется

Добавлено через 1 минуту
A_Kamolins
ну да правильно
Unifan
 Аватар для Unifan
0 / 0 / 0
Регистрация: 11.08.2014
Сообщений: 40
15.08.2014, 18:33  [ТС]     Ступор в возврате указателей и ссылок #6
Спасибо, спасибо большое. Да, я понимаю зачем нужны параметры-ссылки или параметры указатели, но зачем нужны функции, коотрые предворены амперсандом(&), т. е. Почему мы не можем вернуть (return &переменная) без вышеперечисленного действия?
Lynatik001
 Аватар для Lynatik001
34 / 28 / 2
Регистрация: 28.09.2012
Сообщений: 560
15.08.2014, 18:35     Ступор в возврате указателей и ссылок #7
Цитата Сообщение от Unifan Посмотреть сообщение
Спасибо, спасибо большое. Да, я понимаю зачем нужны параметры-ссылки или параметры указатели, но зачем нужны функции, коотрые предворены амперсандом(&), т. е. Почему мы не можем вернуть (return &переменная) без вышеперечисленного действия?
Впервые вижу что бы перед функцией была ссылка.
A_Kamolins
 Аватар для A_Kamolins
4 / 4 / 4
Регистрация: 15.08.2014
Сообщений: 30
15.08.2014, 18:36     Ступор в возврате указателей и ссылок #8
Не совсем понял ваш вопрос. Напишите какой-нибудь пример кодом и задайте по нему вопрос, думаю так будет проще понять вас
Unifan
 Аватар для Unifan
0 / 0 / 0
Регистрация: 11.08.2014
Сообщений: 40
15.08.2014, 18:36  [ТС]     Ступор в возврате указателей и ссылок #9
int &func (//...) {//...}
Lynatik001
 Аватар для Lynatik001
34 / 28 / 2
Регистрация: 28.09.2012
Сообщений: 560
15.08.2014, 18:37     Ступор в возврате указателей и ссылок #10
Цитата Сообщение от Unifan Посмотреть сообщение
Почему мы не можем вернуть (return &переменная) без вышеперечисленного действия?
во 1 покажите код функции, во 2 есть кнопочка С++ ложите код туда в эти теги написав на форуме
C++
1
вот пример
[ CPP ][ /CPP ] - без пропусков
Gwini
10 / 10 / 3
Регистрация: 08.03.2014
Сообщений: 70
15.08.2014, 18:39     Ступор в возврате указателей и ссылок #11
В общем случае если функция принимает ссылку на обычную переменную или объект то вы работаете с этой переменной или объектом напрямую. То есть формальный параметер функции выступает псевдонимом настоящей переменной и не выполняется лишнего копирования как в случае передачи по значению(то есть без ссылки). Если говорить о возвращении:
C++
1
ostream& operator<<(ostream &stream_left, class_name obj_right )
в этом случае возвращается ссылка на объект так как он существует вне функции и это делается что бы лишний раз не происходило копирование во временный объект. Нужно помнить что возвращать ссылку на временный объект созданый в функцие нельзя, так как переменная на которую вы будете ссылатся будет уничтожена после завершения работы функции.

В случае указателя копирование выполняется всегда, т.к. указатель это обычная переменная типа "указатель на тип". Но в случае указателя копируется адрес переменной и если передать адрес например перемнной int x=77 в функцию которая принимает указатель на int то вы так же будете работать напрямую с этой переменной, но ссылки безпопаснее и удобнее в этом случае.
A_Kamolins
 Аватар для A_Kamolins
4 / 4 / 4
Регистрация: 15.08.2014
Сообщений: 30
15.08.2014, 18:40     Ступор в возврате указателей и ссылок #12
этот & значит, что функция должна возвращать адрес переменной типа int всего навсего
Unifan
 Аватар для Unifan
0 / 0 / 0
Регистрация: 11.08.2014
Сообщений: 40
15.08.2014, 18:43  [ТС]     Ступор в возврате указателей и ссылок #13
Допустим у нас есть такой код.
Почему operator объявлен с амперсандом, как поток может возвращаться?
C++ (Qt)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
#include <iostream>
using namespace std;
 
class ThreeD {
public:
    int x, y, z;
    ThreeD(int a, int b, int c) { x = a; y = b; z = c; }
};
 
ostream &operator<<(ostream &stream, ThreeD obj)
{
    stream << obj.x << endl;
    stream << obj.y << endl;
    stream << obj.z << endl;
 
    return stream;
}
 
int main()
{
    ThreeD a(1, 2, 3);
    cout << a;
 
 
    system("pause");
    return 0;
}
Gwini
10 / 10 / 3
Регистрация: 08.03.2014
Сообщений: 70
15.08.2014, 18:47     Ступор в возврате указателей и ссылок #14
Цитата Сообщение от Unifan Посмотреть сообщение
Почему operator объявлен с амперсандом, как поток может возвращаться?
C++
1
ostream& operator<<(ostream &stream, ThreeD obj)
Вот так думаю понятнее. Здесь возвращается ссылка на объект типа ostream.
Blueeyer
12 / 12 / 1
Регистрация: 09.10.2013
Сообщений: 220
15.08.2014, 18:49     Ступор в возврате указателей и ссылок #15
Gwini, ну это до вас уже было сказано выше
Gwini
10 / 10 / 3
Регистрация: 08.03.2014
Сообщений: 70
15.08.2014, 18:58     Ступор в возврате указателей и ссылок #16
Цитата Сообщение от Unifan Посмотреть сообщение
как поток может возвращаться?
он и не возвращается. Возвращается принятый функцией объект, например cout, cerr, clog. Этот обьект создан в файле iostream, то есть он существует еще до начала работы функции и возвращается ссылка на него что бы не было лишнего копирования.

Добавлено через 5 минут
Поток вообще здесь ни при чем. Он никуда не двигается, а открывается в случае работы с ним (например ты вводишь значение) и закрывается по ее завершению. А класы ostream и istream а также их наследники и базовый клас ios_base предоставляют методы для управления этим потоком.
Unifan
 Аватар для Unifan
0 / 0 / 0
Регистрация: 11.08.2014
Сообщений: 40
15.08.2014, 19:15  [ТС]     Ступор в возврате указателей и ссылок #17
Благодарю. Спасибо всем
St1f1er
2 / 2 / 0
Регистрация: 08.08.2014
Сообщений: 14
15.08.2014, 20:27     Ступор в возврате указателей и ссылок #18
Цитата Сообщение от Unifan Посмотреть сообщение
Допустим у нас есть такой код.
Почему operator объявлен с амперсандом, как поток может возвращаться?
C++ (Qt)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
#include <iostream>
using namespace std;
 
class ThreeD {
public:
    int x, y, z;
    ThreeD(int a, int b, int c) { x = a; y = b; z = c; }
};
 
ostream &operator<<(ostream &stream, ThreeD obj)
{
    stream << obj.x << endl;
    stream << obj.y << endl;
    stream << obj.z << endl;
 
    return stream;
}
 
int main()
{
    ThreeD a(1, 2, 3);
    cout << a;
 
 
    system("pause");
    return 0;
}
Мне кажется вы еще не учили перегрузку операторов.
gru74ik
Модератор
 Аватар для gru74ik
3121 / 1347 / 167
Регистрация: 20.02.2013
Сообщений: 3,852
Записей в блоге: 17
15.08.2014, 22:33     Ступор в возврате указателей и ссылок #19
Сообщение было отмечено автором темы, экспертом или модератором как ответ
Тут понимание складывается, на мой взгляд, из нескольких нюансов:
  1. трактовка символа
    Кликните здесь для просмотра всего текста
    Так называемая перегрузка операторов (operator overloading).
    В некоторых случаях & трактуется как оператор взятия адреса (address-of operator), а в других, как ссылка (reference). Так же и символ * иногда трактуется операция умножения, а иногда как указатель.

  2. особенности синтаксиса (разные варианты записи)
    Кликните здесь для просмотра всего текста

    Дополнительную путаницу могут вносить разные варианты записи указателей и ссылок:
    C++
    1
    2
    3
    4
    5
    6
    7
    8
    9
    
    int *ptr;    // указатель на тип int - один из вариантов записи
    int* ptr;    // указатель на тип int - другой вариант записи
    int * ptr;   // указатель на тип int - третий вариант записи
     
    int var;           // переменная с именем "var" типа int
    int &refvar = var; // refvar - ссылка на переменную var
    // иначе говоря, задано альтернативное имя (refvar) для переменной var
    int& refvar = var;  // вариант записи
    int & refvar = var; // вариант записи
    Кроме того, новичка могут смущать названия классов из стандартной библиотеки. Например, такая запись может быть вполне понятной:
    C++
    1
    
    double &rdvar = dvar; // ссылка на переменную типа double
    а вот такое уже вгоняет в ступор:
    C++
    1
    
    ostream &stream // ссылка на объект типа ostream

  3. разные синонимы в терминологии
    Кликните здесь для просмотра всего текста

    Иногда то же самое, объяснённое другими словами способно как внести ясность, так и запутать. Например, мне при изучении темы указателей оказался более понятен термин операция взятия значения, чем разыменование. А в теме про функции обилие синонимов прототип (объявление), определение (реализация) поначалу только запутало.

  4. пошаговая проработка коротких и простых практических примеров
    Кликните здесь для просмотра всего текста

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

  5. объяснение одних и те же тем у разных авторов
    Кликните здесь для просмотра всего текста

    Иногда полезно прочитать что-то, что доходит с трудом, у другого автора.
MoreAnswers
Эксперт
37091 / 29110 / 5898
Регистрация: 17.06.2006
Сообщений: 43,301
16.08.2014, 22:40     Ступор в возврате указателей и ссылок
Еще ссылки по теме:

Реализация программы с использованием ссылок и указателей C++
C++ Вектор ссылок и вектор указателей
C++ Демонстрация работы ссылок, указателей или дескрипторов

Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
gru74ik
Модератор
 Аватар для gru74ik
3121 / 1347 / 167
Регистрация: 20.02.2013
Сообщений: 3,852
Записей в блоге: 17
16.08.2014, 22:40     Ступор в возврате указателей и ссылок #20
del
Yandex
Объявления
16.08.2014, 22:40     Ступор в возврате указателей и ссылок
Ответ Создать тему
Опции темы

Текущее время: 21:24. Часовой пояс GMT +3.
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2016, vBulletin Solutions, Inc.
Рейтинг@Mail.ru