This might do the job unless your class has public data members.
Basically, the idea is not to restrict the construction of the wrapper but to make sure that instances can be used (just like you said) only as long as they are temporary values. One can achieve this by overloading all methods and deleting (or making them private) those that refer to const&.
Here's a simple example:
class Wrapper
{
public:
Wrapper() = default;
Wrapper(const std::string& name) : name(name) {}
void process() && { std::cout << "Greetings from " << name << std::endl; }
// Only temporary instances of this class are allowed!
void process() const & = delete;
private:
std::string name;
};
And some use cases:
Wrapper("John").process(); // intended use case
Wrapper j; // create whatever you want
j.process(); // error C2280: 'void Wrapper::process(void) const &': attempting to reference a deleted function
std::move(j).process(); // this is still possible
const Wrapper& t = Wrapper(); // bind the temporary to a const reference - not a problem because ...
t.process(); // error C2280: 'void Wrapper::process(void) const &': attempting to reference a deleted function
The obvious disadvantages are:
- You have to overload every public member function.
- The error message is delayed and not very informative.
A similar thing has been done in the standard. The make routines for std::reference_wrapper do not accept temporaries.
Note that they considered another subtlety: the overload uses const T&& instead of T&&. This can be important in our case as well. For example, if your wrapper is deliberately designed to be noncopyable and you use make routines such as
const Wrapper make_wrapper();
instead of
Wrapper make_wrapper();
In this case, you might want to replace
void process() &&;
by
void process() const &&;