I have a functor class that has a member buffer.
Due to the semantics, it makes sense that this buffer is mutable.
(it is, for example an std::vector
that is used for .reserve
and .capacity
only)
struct F{
mutable std::vector<double> buffer_;
double operator(double const&) const{... reuse buffer_ ...;}
};
Used as F f; for(double d = 0; ; ++d) f(d);
Now, if for some reason I have a buffer available when F is constructed, I would like buffer_
to be a reference.
The generalized code is
template<class Vector = std::vector<double>> // Vector can be also std::vector<double>&&
struct F{
mutable Vector buffer_;
double operator(double const&) const{... reuse buffer_ ...;}
};
Which I can use as F<std::vector<double>> f; for(...) f(d);
.
However I cannot make it work as
std::vector<double> existing buffer;
F<std::vector<double>&> f{existing_buffer};
for(...) f(d);
because buffer_ cannot be declared as a ‘mutable’ reference
.
(the member would be effectively a forbidden mutable std::vector<double>& buffer_
.)
How can I make the code generic when the member is posibly a mutable value but also can be reference?
I could have two specializations of F
(one for types and one for references), but I am curious if I can have it one single definition.
template<class Vector = std::vector<double>>
struct F{
mutable Vector buffer_;
template<class... Args>
double operator()(double const& d) const{...}
};
template<class Vector>
struct F<Vector&>{
Vector& buffer_;
template<class... Args>
double operator()(double const& d) const{...}
};
(I think mutable should be ignored for reference types, for generic code.)