I have an object Foo owned by Owner and no one else. I create an object of class Derived that inherits Owner, passing it a unique_ptr to a newly created Foo. Derived has a member of class User that also needs to use Foo, but doesn't own it, so it gets only a raw pointer to it.
#include <memory>
#include <iostream>
using namespace std;
struct Foo {
void talk() { cout << "foo" << endl; }
};
struct User {
Foo *foo;
User(Foo *_foo): foo(_foo) {};
void use() { foo->talk(); } //potential disaster if foo's memory has changed
};
struct Owner {
unique_ptr<Foo> foo;
Owner(unique_ptr<Foo> _foo): foo(move(_foo)) {};
};
struct Derived : public Owner {
User user;
Derived(unique_ptr<Foo> _foo)
: Owner {move(_foo)},
user{_foo.get()} //potential disaster: _foo has already been move()'d, can't get()!
{};
void use() { user.use(); };
};
int main() {
Derived d(make_unique<Foo>());
//do other stuff
d.use(); //potential disaster
}
The problem is that in the initialization list of Derived, I need to move() the Foo to pass it to Owner's constructor (which takes a unique_ptr<Foo>, because it is the owner), and also pass a raw pointer to the Foo to User. But by the time the User gets initialized, the unique_ptr<Foo> has already been moved and foo.get() may point to an invalid location!
What's a good way to make sure User gets a valid (non-owning) pointer to Foo and Owner still gets its unique_ptr<Foo>?
Aucun commentaire:
Enregistrer un commentaire