Commit b7ceff06 by Dino Radakovic Committed by Copybara-Service

Release absl::AnyInvocable

AnyInvocable is a C++11 compatible equivalent of the C++23 [std::move_only_function](https://en.cppreference.com/w/cpp/utility/functional/move_only_function/move_only_function).
Although this implementation matches an intermediate draft revision of the standard (http://wg21.link/p0288r5), it is neither a standard tracking type nor a seamless backfill type.

PiperOrigin-RevId: 455494585
Change-Id: If01565f8eecc78eee38fb794ef142b32b31abc7c
parent 53a90f07
...@@ -109,9 +109,11 @@ set(ABSL_INTERNAL_DLL_FILES ...@@ -109,9 +109,11 @@ set(ABSL_INTERNAL_DLL_FILES
"debugging/internal/symbolize.h" "debugging/internal/symbolize.h"
"debugging/internal/vdso_support.cc" "debugging/internal/vdso_support.cc"
"debugging/internal/vdso_support.h" "debugging/internal/vdso_support.h"
"functional/any_invocable.h"
"functional/internal/front_binder.h" "functional/internal/front_binder.h"
"functional/bind_front.h" "functional/bind_front.h"
"functional/function_ref.h" "functional/function_ref.h"
"functional/internal/any_invocable.h"
"functional/internal/function_ref.h" "functional/internal/function_ref.h"
"hash/hash.h" "hash/hash.h"
"hash/internal/city.h" "hash/internal/city.h"
...@@ -388,6 +390,7 @@ set(ABSL_INTERNAL_DLL_TARGETS ...@@ -388,6 +390,7 @@ set(ABSL_INTERNAL_DLL_TARGETS
"kernel_timeout_internal" "kernel_timeout_internal"
"synchronization" "synchronization"
"thread_pool" "thread_pool"
"any_invocable"
"bind_front" "bind_front"
"function_ref" "function_ref"
"atomic_hook" "atomic_hook"
......
...@@ -26,6 +26,40 @@ package(default_visibility = ["//visibility:public"]) ...@@ -26,6 +26,40 @@ package(default_visibility = ["//visibility:public"])
licenses(["notice"]) licenses(["notice"])
cc_library( cc_library(
name = "any_invocable",
srcs = ["internal/any_invocable.h"],
hdrs = ["any_invocable.h"],
copts = ABSL_DEFAULT_COPTS,
linkopts = ABSL_DEFAULT_LINKOPTS,
deps = [
"//absl/base:base_internal",
"//absl/base:config",
"//absl/base:core_headers",
"//absl/meta:type_traits",
"//absl/utility",
],
)
cc_test(
name = "any_invocable_test",
srcs = [
"any_invocable_test.cc",
"internal/any_invocable.h",
],
copts = ABSL_TEST_COPTS,
linkopts = ABSL_DEFAULT_LINKOPTS,
deps = [
":any_invocable",
"//absl/base:base_internal",
"//absl/base:config",
"//absl/base:core_headers",
"//absl/meta:type_traits",
"//absl/utility",
"@com_google_googletest//:gtest_main",
],
)
cc_library(
name = "bind_front", name = "bind_front",
srcs = ["internal/front_binder.h"], srcs = ["internal/front_binder.h"],
hdrs = ["bind_front.h"], hdrs = ["bind_front.h"],
...@@ -86,6 +120,7 @@ cc_test( ...@@ -86,6 +120,7 @@ cc_test(
tags = ["benchmark"], tags = ["benchmark"],
visibility = ["//visibility:private"], visibility = ["//visibility:private"],
deps = [ deps = [
":any_invocable",
":function_ref", ":function_ref",
"//absl/base:core_headers", "//absl/base:core_headers",
"@com_github_google_benchmark//:benchmark_main", "@com_github_google_benchmark//:benchmark_main",
......
...@@ -16,6 +16,42 @@ ...@@ -16,6 +16,42 @@
absl_cc_library( absl_cc_library(
NAME NAME
any_invocable
SRCS
"internal/any_invocable.h"
HDRS
"any_invocable.h"
COPTS
${ABSL_DEFAULT_COPTS}
DEPS
absl::base_internal
absl::config
absl::core_headers
absl::type_traits
absl::utility
PUBLIC
)
absl_cc_test(
NAME
any_invocable_test
SRCS
"any_invocable_test.cc"
"internal/any_invocable.h"
COPTS
${ABSL_DEFAULT_COPTS}
DEPS
absl::any_invocable
absl::base_internal
absl::config
absl::core_headers
absl::type_traits
absl::utility
GTest::gmock_main
)
absl_cc_library(
NAME
bind_front bind_front
SRCS SRCS
"internal/front_binder.h" "internal/front_binder.h"
......
...@@ -18,6 +18,7 @@ ...@@ -18,6 +18,7 @@
#include "benchmark/benchmark.h" #include "benchmark/benchmark.h"
#include "absl/base/attributes.h" #include "absl/base/attributes.h"
#include "absl/functional/any_invocable.h"
#include "absl/functional/function_ref.h" #include "absl/functional/function_ref.h"
namespace absl { namespace absl {
...@@ -62,6 +63,12 @@ void BM_TrivialFunctionRef(benchmark::State& state) { ...@@ -62,6 +63,12 @@ void BM_TrivialFunctionRef(benchmark::State& state) {
} }
BENCHMARK(BM_TrivialFunctionRef); BENCHMARK(BM_TrivialFunctionRef);
void BM_TrivialAnyInvocable(benchmark::State& state) {
ConstructAndCallFunctionBenchmark<AnyInvocable<void()>>(state,
TrivialFunctor{});
}
BENCHMARK(BM_TrivialAnyInvocable);
void BM_LargeStdFunction(benchmark::State& state) { void BM_LargeStdFunction(benchmark::State& state) {
ConstructAndCallFunctionBenchmark<std::function<void()>>(state, ConstructAndCallFunctionBenchmark<std::function<void()>>(state,
LargeFunctor{}); LargeFunctor{});
...@@ -73,6 +80,13 @@ void BM_LargeFunctionRef(benchmark::State& state) { ...@@ -73,6 +80,13 @@ void BM_LargeFunctionRef(benchmark::State& state) {
} }
BENCHMARK(BM_LargeFunctionRef); BENCHMARK(BM_LargeFunctionRef);
void BM_LargeAnyInvocable(benchmark::State& state) {
ConstructAndCallFunctionBenchmark<AnyInvocable<void()>>(state,
LargeFunctor{});
}
BENCHMARK(BM_LargeAnyInvocable);
void BM_FunPtrStdFunction(benchmark::State& state) { void BM_FunPtrStdFunction(benchmark::State& state) {
ConstructAndCallFunctionBenchmark<std::function<void()>>(state, FreeFunction); ConstructAndCallFunctionBenchmark<std::function<void()>>(state, FreeFunction);
} }
...@@ -83,6 +97,11 @@ void BM_FunPtrFunctionRef(benchmark::State& state) { ...@@ -83,6 +97,11 @@ void BM_FunPtrFunctionRef(benchmark::State& state) {
} }
BENCHMARK(BM_FunPtrFunctionRef); BENCHMARK(BM_FunPtrFunctionRef);
void BM_FunPtrAnyInvocable(benchmark::State& state) {
ConstructAndCallFunctionBenchmark<AnyInvocable<void()>>(state, FreeFunction);
}
BENCHMARK(BM_FunPtrAnyInvocable);
// Doesn't include construction or copy overhead in the loop. // Doesn't include construction or copy overhead in the loop.
template <typename Function, typename Callable, typename... Args> template <typename Function, typename Callable, typename... Args>
void CallFunctionBenchmark(benchmark::State& state, const Callable& c, void CallFunctionBenchmark(benchmark::State& state, const Callable& c,
...@@ -114,6 +133,12 @@ void BM_TrivialArgsFunctionRef(benchmark::State& state) { ...@@ -114,6 +133,12 @@ void BM_TrivialArgsFunctionRef(benchmark::State& state) {
} }
BENCHMARK(BM_TrivialArgsFunctionRef); BENCHMARK(BM_TrivialArgsFunctionRef);
void BM_TrivialArgsAnyInvocable(benchmark::State& state) {
CallFunctionBenchmark<AnyInvocable<void(int, int, int)>>(
state, FunctorWithTrivialArgs{}, 1, 2, 3);
}
BENCHMARK(BM_TrivialArgsAnyInvocable);
struct FunctorWithNonTrivialArgs { struct FunctorWithNonTrivialArgs {
void operator()(std::string a, std::string b, std::string c) const { void operator()(std::string a, std::string b, std::string c) const {
benchmark::DoNotOptimize(&a); benchmark::DoNotOptimize(&a);
...@@ -138,6 +163,14 @@ void BM_NonTrivialArgsFunctionRef(benchmark::State& state) { ...@@ -138,6 +163,14 @@ void BM_NonTrivialArgsFunctionRef(benchmark::State& state) {
} }
BENCHMARK(BM_NonTrivialArgsFunctionRef); BENCHMARK(BM_NonTrivialArgsFunctionRef);
void BM_NonTrivialArgsAnyInvocable(benchmark::State& state) {
std::string a, b, c;
CallFunctionBenchmark<
AnyInvocable<void(std::string, std::string, std::string)>>(
state, FunctorWithNonTrivialArgs{}, a, b, c);
}
BENCHMARK(BM_NonTrivialArgsAnyInvocable);
} // namespace } // namespace
ABSL_NAMESPACE_END ABSL_NAMESPACE_END
} // namespace absl } // namespace absl
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment