What the OP describes here is a common C++ pattern known as "scope guard" (check "Solution 4" in <a href="http://drdobbs.com/184403758" rel="nofollow">http://drdobbs.com/184403758</a>). It was possible to implement it in C++03 with some tricks but C++11 lambdas make it much easier.<p>This is a very nice small implementation but, as always with C++, devil is in the details:<p>* Creation of an std::function needs a dynamic allocation, so if the allocation fails an exception will be thrown and if the <i>finally</i> is guarding a resource, the resource will be leaked<p>* std::function has a non-negligible calling overhead, hence this should not be used in performance-sensitive code<p>* Checking a condition inside the finally clause is not very elegant, a better idiom in C++ is to support <i>dismissing</i> a scope guard.<p>* The finallyClause may throw an exception, and since it is called in a destructor this is generally considered a bad idea. I don't know what could happen in this case, but some scope guard implementations I've seen catch the exception and explicitly call std::terminate(). I guess this is for performance reasons, because the destructor can be declared nothrow.<p>Here there is a more complex implementation, which addresses most of the corner cases:<p><a href="http://channel9.msdn.com/Shows/Going+Deep/C9-Lectures-Stephan-T-Lavavej-Advanced-STL-6-of-n#c634477472460000000" rel="nofollow">http://channel9.msdn.com/Shows/Going+Deep/C9-Lectures-Stepha...</a>
I’ve done this before, and this version has a significant flaw: it is not exception-safe. The destructor should not read as it does:<p><pre><code> ~finally() {
finallyClause();
}
</code></pre>
This allows exceptions thrown by finallyClause() to propagate out of the destructor, which, if an exception is already being thrown, will result in a call to std::terminate(), causing the application to die horrifically. Because C++ kinda-should’ve-but-really-doesn’t have checked exceptions, we must simply discard them:<p><pre><code> ~finally() {
try { finallyClause(); } catch (...) {}
}
</code></pre>
You can also avoid problems with exceptions and std::function’s dynamic allocation by using a template instead:<p><pre><code> template<class F>
class finally_type {
public:
explicit finally_type(F f) : function(f) {}
~finally_type() { try { function(); } catch (...) {} }
private:
finally_type(const finally_type&);
finally_type& operator=(const finally_type&);
F function;
};
template<class F>
finally_type<F> finally(F f) { return finally_type<F>(f); }
</code></pre>
This can be used like so:<p><pre><code> void test() {
int* i = new int;
auto cleanup = finally([i]() { delete i; });
may_throw();
}
</code></pre>
Finally (har!) the equivalent idiom in C++03:<p><pre><code> void test() {
int* i = new int;
struct finally {
finally(int* i) : i(i) {}
~finally() { delete i; }
int* i;
} cleanup(i);
may_throw();
}</code></pre>