Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to correctly manage resources with move semantics?

struct foo{
  int* i;
  foo(): i(new int(42)){}
  foo(const foo&) = delete;
  foo(foo&&) = default;
  ~foo(){
    std::cout << "destructor: i" << std::endl;
    delete(i);
  }
};
int main()
{
  foo f;
  auto sp_f = std::make_shared<foo>(std::move(f));
}

This is bad because it seems that the destructor of f will be called once it moves into the shared_ptr. The shared_ptr will have a deleted pointer and will delete it after it goes out of scope, which means the pointer will be deleted two times.

How do I avoid this problem?

like image 796
Maik Klein Avatar asked Sep 06 '25 12:09

Maik Klein


1 Answers

You need to define the move constructor to prevent deletion from the moved-from object:

foo(foo&& f): i(f.i) {
  f.i = nullptr;
}

Now when to destructor of the old object is run, it won't delete the i, since deleting a null pointer is a no-op.

You should also define a move assignment operator and delete the copy assignment operator too.

like image 78
emlai Avatar answered Sep 08 '25 16:09

emlai