Можно ли в вектор отправлять объект по ссылке?
Я ранее активно использовал C#, но понадобилось создать приложение на C++. И я не пойму, почему вектор не реагирует на изменения элементов.
Приведу пример из C#:
class Program
{
static void Main(string[] args)
{
List<Book> books = new List<Book>();
Book book1 = new Book();
books.Add(book1);
book1.id = 5; // на это изменение реагирует список *books*. То есть его элемент тоже теперь имеет id = 5
}
}
class Book
{
public int id = 1;
}
В данном случае элемент списка и объект ссылаются на один адрес, но у меня не получается сделать то же самое в C++
class Book
{
public:
int id = 1;
};
int main()
{
vector<Book> books;
Book book1 = Book();
books.push_back(book1);
book1.id = 5;
cout << &book1 << " " << &books[0] << endl;
return 0;
}
Но справедливо заметил, что элемент вектора и book1 ссылаются на разные адреса. И я не пойму, почему там разные адреса, хотя в объявлении функции push_back() у вектора сказано, что объект получает ссылку, а не копию.
Если это невозможно в принципе, то нет ли обходного пути, чтоб напрямую не обращаться к элементу вектора?
Ответы (1 шт):
В C++ контейнеры хранят объекты по значению. Для достижения поведения схожего с C#, достаточно использовать контейнер указателей, но чтобы не было заморочек с владением и временем жизни объектов, на которые эти указатели будут указывать, должны быть не обычные сырые сишные указатели, а их "умные" компаньоны. В данном случае вам проще всего подойдёт std::shared_ptr.
std::vector<std::shared_ptr<Book>> books;
auto book1 = std::make_shared<Book>();
books.push_back(book1);
book1->id = 5;
std::cout << book1.get() << " " << books[0].get() << '\n';