#pragma once #include #include template class ScopeGuard { private: TCleanupFunc mFunc; bool mDismissed = false; public: /// Specifically left this implicit so that constructs like /// \code /// ScopeGuard sg = [&]() { res.Cleanup(); }; /// \endcode /// would work. It is highly discourage and unlikely that one would want to use ScopeGuard as a function /// parameter, so the normal argument that implicit conversion are harmful doesn't really apply here. ScopeGuard(TCleanupFunc func) : mFunc{ std::move(func) } { } ~ScopeGuard() { if (!mDismissed) { mFunc(); } } void Dismiss() noexcept { mDismissed = true; } }; #define DEFER ScopeGuard UNIQUE_NAME(scopeGuard) = [&]()