Форум программистов, компьютерный форум, киберфорум
С++ для начинающих
Войти
Регистрация
Восстановить пароль
 
Рейтинг 5.00/13: Рейтинг темы: голосов - 13, средняя оценка - 5.00
0 / 0 / 0
Регистрация: 06.08.2018
Сообщений: 22
1

Как метод класса возвращает обьект, который является одним из полей данного класса?

16.08.2019, 21:19. Показов 2603. Ответов 5

Привет!
Когда я пытался изменять объект который вернул мне метод класса, полем или свойством которого был этот обьект, я как будто получал копию этого объекта. Он не изменялся. Тогда я попробовал возвращать ссылку на этот обьект - все работает.

упрощенный пример

C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
// описание класса SomeObject думаю не имеет значения
 
class A
{
   SomeObject object;
public:
   SomeObject getSomeObject()
   {
      return object;
   }
}
 
main()
{
   A objA;
   objA.getSomeObject().changes();
   // вот здесь с обьектом object внутри класса A ничего не происходит.
}
Делаем так
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
// описание класса SomeObject думаю не имеет значения
 
class A
{
   SomeObject object;
public:
   SomeObject* getSomeObject()
   {
      //теперь передаю ссылку
      return &object;
   }
}
 
main()
{
   A objA;
   objA.getSomeObject()->changes();
   // объект изменяется все как положено
}
Так вот поясните, почему-то я раньше не сталкивался с тем, что return возвращает копии... как это работает, по полочкам?
Заранее спасибо!
0

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

Лучшие ответы (1)
Programming
Эксперт
94731 / 64177 / 26122
Регистрация: 12.04.2006
Сообщений: 116,782
16.08.2019, 21:19
Ответы с готовыми решениями:

Как получить значение из метода класса, если метод возвращает указатель?
Всем привет. Как получить значение из метода класса, если метод возвращает указатель? Вот тут я...

Как передать в метод класса Menu указатель на метод дочернего класса?
Как передать в метод базового класса указатель на метод дочернего: class Menu() { protected: ...

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

Как задать размер массива, который является членом класса, через конструктор?
Почему так? И как же тогда задать размер этого массива? class Test { public: Test(int...

5
6737 / 4537 / 1838
Регистрация: 07.05.2019
Сообщений: 13,725
Записей в блоге: 1
16.08.2019, 21:29 2
Цитата Сообщение от KRC Посмотреть сообщение
Когда я пытался изменять объект который вернул мне метод класса, полем или свойством которого был этот обьект, я как будто получал копию этого объекта. Он не изменялся. Тогда я попробовал возвращать ссылку на этот обьект - все работает.
Ну да, когда ты делаешь копию, а потом её изменяешь, то оригинальный объект не изменится. Когда ты не делаешь копию, а возвращаешь ссылку на оригинальный объект, то можешь его изменить.
Цитата Сообщение от KRC Посмотреть сообщение
Так вот поясните, почему-то я раньше не сталкивался с тем, что return возвращает копии... как это работает, по полочкам?
По-полочкам:
Если ты делаешь вот так SomeObject getSomeObject(), то возвращается копия
Если SomeObject &getSomeObject() - то ссылка
0
nd2
3415 / 2795 / 1251
Регистрация: 29.01.2016
Сообщений: 9,426
16.08.2019, 23:10 3
Цитата Сообщение от KRC Посмотреть сообщение
C++
1
2
3
4
5
   SomeObject* getSomeObject()
   {
      //теперь передаю ссылку
      return &object;
   }
Это адрес, а не ссылка. Вот так ссылка:
C++
1
2
3
4
5
6
 
   SomeObject& getSomeObject()
   {
      //теперь передаю ссылку
      return object;
   }
1
0 / 0 / 0
Регистрация: 06.08.2018
Сообщений: 22
17.08.2019, 10:41  [ТС] 4
Цитата Сообщение от oleg-m1973 Посмотреть сообщение
Ну да, когда ты делаешь копию, а потом её изменяешь, то оригинальный объект не изменится. Когда ты не делаешь копию, а возвращаешь ссылку на оригинальный объект, то можешь его изменить.
Цитата Сообщение от oleg-m1973 Посмотреть сообщение
По-полочкам:
Если ты делаешь вот так SomeObject getSomeObject(), то возвращается копия
Если SomeObject &getSomeObject() - то ссылка
Ты просто написал то, что я написал...

Цитата Сообщение от nd2 Посмотреть сообщение
Это адрес, а не ссылка. Вот так ссылка:
да, так будет ловчее, спасибо.
0
Комп_Оратор)
Эксперт по математике/физике
8719 / 4425 / 598
Регистрация: 04.12.2011
Сообщений: 13,256
Записей в блоге: 16
17.08.2019, 12:09 5
Лучший ответ Сообщение было отмечено KRC как решение

Решение

Цитата Сообщение от KRC Посмотреть сообщение
Так вот поясните, почему-то я раньше не сталкивался с тем, что return возвращает копии... как это работает, по полочкам?
Заранее спасибо!
KRC, по полочкам - в книгах. А тут без RVO и move семантики, и так придётся кое-что написать. Когда в функции создаётся локальный объект, то функция не может вернуть ни этот объект ни указатель ни ссылку на него. Это потому, что при схлопывании области стека (рабочей области) всё будет уничтожено. Поэтому для возврата значения предусмотрен механизм, который реализуется копированием локального объекта в объект заготовленный для этого в месте вызова функции.
Для поля класса можно сделать возврат как по ссылке так и по указателю, поскольку время жизни поля определено временем жизни его объекта и не зависит от работы стека по вызову и завершению работы метода. Поля объектов находятся в области объекта и доступны методу, но механизм стека для конкретного метода к ним не относится. Тем не менее, если использован возврат по значению, то работает копирующий механизм (см. выше). Это в 2-х словах. Если где-то не был корректен, - меня поправят.

Добавлено через 24 минуты
Цитата Сообщение от IGPIGP Посмотреть сообщение
Поля объектов находятся в области объекта и доступны методу, но механизм стека для конкретного метода к ним не относится.
Тут уместно было бы конкретизировать. Любой метод имеет скрытый параметр - указатель на объект для которого вызывается (this). То есть, доступ для модификации полей у него полон. Но главное, время жизни объекта и его полей не связаны со стеком метода. А при возврате значения - работает механизм копирования. Так же работает возврат по значению объекта принятого по ссылке, например:
C++
1
2
3
4
A foo(A& a)
{
return a;
}
1
0 / 0 / 0
Регистрация: 06.08.2018
Сообщений: 22
18.08.2019, 10:59  [ТС] 6
Цитата Сообщение от IGPIGP Посмотреть сообщение
KRC, по полочкам - в книгах. А тут без RVO и move семантики, и так придётся кое-что написать. Когда в функции создаётся локальный объект, то функция не может вернуть ни этот объект ни указатель ни ссылку на него. Это потому, что при схлопывании области стека (рабочей области) всё будет уничтожено. Поэтому для возврата значения предусмотрен механизм, который реализуется копированием локального объекта в объект заготовленный для этого в месте вызова функции.
Для поля класса можно сделать возврат как по ссылке так и по указателю, поскольку время жизни поля определено временем жизни его объекта и не зависит от работы стека по вызову и завершению работы метода. Поля объектов находятся в области объекта и доступны методу, но механизм стека для конкретного метода к ним не относится. Тем не менее, если использован возврат по значению, то работает копирующий механизм (см. выше). Это в 2-х словах. Если где-то не был корректен, - меня поправят.
Спасибо, все по полочкам)
0
IT_Exp
Эксперт
87844 / 49110 / 22898
Регистрация: 17.06.2006
Сообщений: 92,604
18.08.2019, 10:59

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

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

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

Получить константу из экземпляра класса, который является членом другого класса
class test { const STATUS = 1; } $a = new test(); echo $a::STATUS . PHP_EOL; // работает ...

Как правильно создать массив объектов текущего класса в методе данного класса?
Привет! Ставится задача создания метода, который формирует массив объектов. Правильно ли делать...


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

Или воспользуйтесь поиском по форуму:
6
Ответ Создать тему
Опции темы

КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2021, vBulletin Solutions, Inc.