Reputation: 4114
I have a class with a constructor and a destructor and the following code for both:
class propagation_module{
private:
gsl_interp_accel *xa;
interp2d_spline *interp_s;
public:
propagation_module()
{
std::vector<int> p_N = {1, 2, 3}, z_vec = {1, 2, 3};
xa = gsl_interp_accel_alloc();
interp_s = interp2d_spline_alloc(interp2d_bicubic, p_N.size(), z_vec.size());
}
~propagation_module(){
gsl_interp_accel_free(xa);
interp2d_spline_free(interp_s);
}
}
I would like to replace the pointers with std::unique_ptr-variables, but I do not understand how to implement the free-functions. According to some other questions the following way should work:
class propagation_module
{
private:
std::unique_ptr<gls_interp_accel, decltype(&gsl_interp_accel_free)> xa;
std::unique_ptr<interp2d_spline, decltype(&interp2d_spline_free)> interp_s;
public:
propagation_module()
{
//Same as above
}
//No destructor necessary
}
Is that correct, or did I forget something?
Upvotes: 2
Views: 83
Reputation: 171167
You're halfway there. By default, std::unique_ptr
will default-construct its deleter when none is passed in at unique_ptr
creation time. You provide the correct types for the deleters, but you need to provide their values too:
public:
propagation_module()
{
std::vector<int> p_N = {1, 2, 3}, z_vec = {1, 2, 3};
xa = {gsl_interp_accel_alloc(), &gsl_interp_accel_free};
interp_s = {interp2d_spline_alloc(interp2d_bicubic, p_N.size(), z_vec.size()), &interp2d_spline_free};
}
Alternatively, if you do not want to have to give the correct deleters each time you create a unique pointer, you can create default-constructible wrappers to call the right function:
struct GslInterpAccelFree
{
void operator() (gsl_interp_accel *p) const { gsl_interp_accel_free(p); }
};
struct Interp2dSplineFree
{
void operator() (interp2d_spline *p) const { interp2d_spline_free(p); }
};
class propagation_module
{
private:
std::unique_ptr<gls_interp_accel, GslInterpAccelFree> xa;
std::unique_ptr<interp2d_spline, Interp2dSplineFree> interp_s;
public:
propagation_module()
{
std::vector<int> p_N = {1, 2, 3}, z_vec = {1, 2, 3};
xa.reset(gsl_interp_accel_alloc());
interp_s.reset(interp2d_spline_alloc(interp2d_bicubic, p_N.size(), z_vec.size()));
}
//No destructor necessary
}
Upvotes: 5