Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(2859)

Unified Diff: base/function_util.h

Issue 2090013004: Adds base::WrapFunction to wrap lambdas as base::Callbacks (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Created 4 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « base/base.gypi ('k') | mojo/public/cpp/bindings/tests/sync_method_unittest.cc » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: base/function_util.h
diff --git a/base/function_util.h b/base/function_util.h
new file mode 100644
index 0000000000000000000000000000000000000000..1598804aa73e760407413fdef27e505f402becb4
--- /dev/null
+++ b/base/function_util.h
@@ -0,0 +1,67 @@
+// Copyright 2016 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef BASE_FUNCTION_UTIL_H_
+#define BASE_FUNCTION_UTIL_H_
+
+#include <utility>
+
+#include "base/bind.h"
+#include "base/callback.h"
+
+namespace base {
+
+namespace internal {
+
+template <typename FuncType, typename Result, typename... Args>
+struct FunctionBinderHelper {
+ static Result Run(FuncType func, Args... args) {
yzshen1 2016/06/22 23:05:54 Do we need Args&&... (here and below)?
Ken Rockot(use gerrit already) 2016/06/22 23:14:43 This wouldn't work - we can't for example base::Bi
+ return func(std::forward<Args>(args)...);
+ }
+};
+
+template <typename FuncType, typename... Args>
+struct FunctionBinderHelper<FuncType, void, Args...> {
+ static void Run(FuncType func, Args... args) {
+ func(std::forward<Args>(args)...);
+ }
+};
+
+template <typename CallbackType>
+struct FunctionBinder {};
+
+template <typename ResultType, typename... Args>
+struct FunctionBinder<Callback<ResultType(Args...)>> {
+ template <typename FuncType>
+ static Callback<ResultType(Args...)> BindFunction(FuncType func) {
+ return Bind(
+ &FunctionBinderHelper<FuncType, ResultType, Args...>::Run, func);
+ }
+};
+
+} // namespace internal
+
+// Wraps an arbitrary function as a base::Callback. Note that this requires an
+// explicit specification of the target base::Callback type, but the wrapped
+// function type can be inferred and thus supports wrapping C++11 lambdas.
+//
+// For example:
+//
+// using AddCallback = base::Callback<int(int x, int y)>;
+// AddCallback cb = base::WrapLambda<AddCallback>([](int x, int y) {
+// return x + y;
+// });
+// int z = cb.Run(x, y);
+//
+// NOTE: Do NOT wrap lambdas which capture references of any kind unless it is
+// abundantly clear that this will not lead to subtle bugs, e.g., the wrapped
+// callback cannot possibly outlive the captured references.
+template <typename CallbackType, typename FuncType>
+CallbackType WrapFunction(FuncType func) {
+ return internal::FunctionBinder<CallbackType>::BindFunction(func);
+}
+
+} // namespace base
+
+#endif // BASE_FUNCTION_UTIL_H_
« no previous file with comments | « base/base.gypi ('k') | mojo/public/cpp/bindings/tests/sync_method_unittest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698