From 67cab0c465a201e51192eaf519497f64df1ea5b8 Mon Sep 17 00:00:00 2001 From: Derek Mauro Date: Wed, 19 Mar 2025 10:20:09 -0700 Subject: [PATCH] Cleanups related to benchmarks * Fix many benchmarks to be cc_binary instead of cc_test * Add a few benchmarks for StrFormat * Add benchmarks for Substitute * Add benchmarks for Damerau-Levenshtein distance used in flags PiperOrigin-RevId: 738448552 Change-Id: I521f4b2ef9116c9895b44c32d27e94507380bee8 --- absl/base/BUILD.bazel | 4 +- .../internal/thread_identity_benchmark.cc | 2 +- absl/container/BUILD.bazel | 1 - absl/container/btree_benchmark.cc | 2 +- absl/functional/BUILD.bazel | 4 +- absl/functional/function_type_benchmark.cc | 2 +- absl/numeric/BUILD.bazel | 5 +- absl/numeric/bits_benchmark.cc | 2 +- absl/numeric/int128_benchmark.cc | 2 +- absl/strings/BUILD.bazel | 83 ++++++--- absl/strings/ascii_benchmark.cc | 7 +- absl/strings/charconv_benchmark.cc | 3 +- absl/strings/charset_benchmark.cc | 2 +- absl/strings/escaping_benchmark.cc | 5 +- .../damerau_levenshtein_distance_benchmark.cc | 56 +++++++ absl/strings/internal/memutil_benchmark.cc | 5 +- .../internal/ostringstream_benchmark.cc | 3 +- absl/strings/numbers_benchmark.cc | 2 +- absl/strings/str_cat_benchmark.cc | 26 ++- absl/strings/str_join_benchmark.cc | 5 +- absl/strings/str_replace_benchmark.cc | 5 +- absl/strings/str_split_benchmark.cc | 5 +- absl/strings/string_view_benchmark.cc | 5 +- absl/strings/substitute_benchmark.cc | 158 ++++++++++++++++++ absl/synchronization/BUILD.bazel | 1 - .../internal/graphcycles_benchmark.cc | 5 +- absl/time/BUILD.bazel | 3 +- 27 files changed, 330 insertions(+), 73 deletions(-) create mode 100644 absl/strings/internal/damerau_levenshtein_distance_benchmark.cc create mode 100644 absl/strings/substitute_benchmark.cc diff --git a/absl/base/BUILD.bazel b/absl/base/BUILD.bazel index 5e67a651..83fd607b 100644 --- a/absl/base/BUILD.bazel +++ b/absl/base/BUILD.bazel @@ -699,8 +699,9 @@ cc_test( ], ) -cc_test( +cc_binary( name = "thread_identity_benchmark", + testonly = True, srcs = ["internal/thread_identity_benchmark.cc"], copts = ABSL_TEST_COPTS, linkopts = ABSL_DEFAULT_LINKOPTS, @@ -710,7 +711,6 @@ cc_test( ":base", "//absl/synchronization", "@google_benchmark//:benchmark_main", - "@googletest//:gtest", ], ) diff --git a/absl/base/internal/thread_identity_benchmark.cc b/absl/base/internal/thread_identity_benchmark.cc index 0ae10f2b..419e82db 100644 --- a/absl/base/internal/thread_identity_benchmark.cc +++ b/absl/base/internal/thread_identity_benchmark.cc @@ -12,10 +12,10 @@ // See the License for the specific language governing permissions and // limitations under the License. -#include "benchmark/benchmark.h" #include "absl/base/internal/thread_identity.h" #include "absl/synchronization/internal/create_thread_identity.h" #include "absl/synchronization/internal/per_thread_sem.h" +#include "benchmark/benchmark.h" namespace { diff --git a/absl/container/BUILD.bazel b/absl/container/BUILD.bazel index 37b5f2ac..ccaed1c7 100644 --- a/absl/container/BUILD.bazel +++ b/absl/container/BUILD.bazel @@ -1148,6 +1148,5 @@ cc_binary( "//absl/strings:str_format", "//absl/time", "@google_benchmark//:benchmark_main", - "@googletest//:gtest", ], ) diff --git a/absl/container/btree_benchmark.cc b/absl/container/btree_benchmark.cc index b1525bdc..ee4efbd0 100644 --- a/absl/container/btree_benchmark.cc +++ b/absl/container/btree_benchmark.cc @@ -26,7 +26,6 @@ #include #include -#include "benchmark/benchmark.h" #include "absl/algorithm/container.h" #include "absl/base/internal/raw_logging.h" #include "absl/container/btree_map.h" @@ -42,6 +41,7 @@ #include "absl/strings/cord.h" #include "absl/strings/str_format.h" #include "absl/time/time.h" +#include "benchmark/benchmark.h" namespace absl { ABSL_NAMESPACE_BEGIN diff --git a/absl/functional/BUILD.bazel b/absl/functional/BUILD.bazel index 8296f14a..aeed3b66 100644 --- a/absl/functional/BUILD.bazel +++ b/absl/functional/BUILD.bazel @@ -146,8 +146,9 @@ cc_test( ], ) -cc_test( +cc_binary( name = "function_type_benchmark", + testonly = True, srcs = [ "function_type_benchmark.cc", ], @@ -159,6 +160,5 @@ cc_test( ":function_ref", "//absl/base:core_headers", "@google_benchmark//:benchmark_main", - "@googletest//:gtest", ], ) diff --git a/absl/functional/function_type_benchmark.cc b/absl/functional/function_type_benchmark.cc index 03dc31d8..513233b4 100644 --- a/absl/functional/function_type_benchmark.cc +++ b/absl/functional/function_type_benchmark.cc @@ -16,10 +16,10 @@ #include #include -#include "benchmark/benchmark.h" #include "absl/base/attributes.h" #include "absl/functional/any_invocable.h" #include "absl/functional/function_ref.h" +#include "benchmark/benchmark.h" namespace absl { ABSL_NAMESPACE_BEGIN diff --git a/absl/numeric/BUILD.bazel b/absl/numeric/BUILD.bazel index 4503a157..3c7a02fd 100644 --- a/absl/numeric/BUILD.bazel +++ b/absl/numeric/BUILD.bazel @@ -56,7 +56,6 @@ cc_binary( "//absl/base:core_headers", "//absl/random", "@google_benchmark//:benchmark_main", - "@googletest//:gtest", ], ) @@ -115,8 +114,9 @@ cc_test( ], ) -cc_test( +cc_binary( name = "int128_benchmark", + testonly = True, srcs = ["int128_benchmark.cc"], copts = ABSL_TEST_COPTS, linkopts = ABSL_DEFAULT_LINKOPTS, @@ -125,7 +125,6 @@ cc_test( ":int128", "//absl/base:config", "@google_benchmark//:benchmark_main", - "@googletest//:gtest", ], ) diff --git a/absl/numeric/bits_benchmark.cc b/absl/numeric/bits_benchmark.cc index 2c89afdb..429b4cab 100644 --- a/absl/numeric/bits_benchmark.cc +++ b/absl/numeric/bits_benchmark.cc @@ -15,10 +15,10 @@ #include #include -#include "benchmark/benchmark.h" #include "absl/base/optimization.h" #include "absl/numeric/bits.h" #include "absl/random/random.h" +#include "benchmark/benchmark.h" namespace absl { namespace { diff --git a/absl/numeric/int128_benchmark.cc b/absl/numeric/int128_benchmark.cc index eab1515c..e2e2de58 100644 --- a/absl/numeric/int128_benchmark.cc +++ b/absl/numeric/int128_benchmark.cc @@ -18,9 +18,9 @@ #include #include -#include "benchmark/benchmark.h" #include "absl/base/config.h" #include "absl/numeric/int128.h" +#include "benchmark/benchmark.h" namespace { diff --git a/absl/strings/BUILD.bazel b/absl/strings/BUILD.bazel index cb8d9008..ddc115dc 100644 --- a/absl/strings/BUILD.bazel +++ b/absl/strings/BUILD.bazel @@ -172,8 +172,9 @@ cc_test( ], ) -cc_test( +cc_binary( name = "escaping_benchmark", + testonly = True, srcs = [ "escaping_benchmark.cc", "internal/escaping_test_common.h", @@ -185,7 +186,6 @@ cc_test( ":strings", "//absl/base:raw_logging_internal", "@google_benchmark//:benchmark_main", - "@googletest//:gtest", ], ) @@ -241,8 +241,9 @@ cc_test( ], ) -cc_test( +cc_binary( name = "ascii_benchmark", + testonly = True, srcs = ["ascii_benchmark.cc"], copts = ABSL_TEST_COPTS, tags = ["benchmark"], @@ -250,7 +251,6 @@ cc_test( deps = [ ":strings", "@google_benchmark//:benchmark_main", - "@googletest//:gtest", ], ) @@ -268,8 +268,25 @@ cc_test( ], ) -cc_test( +cc_binary( + name = "damerau_levenshtein_distance_benchmark", + testonly = True, + srcs = [ + "internal/damerau_levenshtein_distance_benchmark.cc", + ], + copts = ABSL_TEST_COPTS, + linkopts = ABSL_DEFAULT_LINKOPTS, + tags = ["benchmark"], + visibility = ["//visibility:private"], + deps = [ + ":strings", + "@google_benchmark//:benchmark_main", + ], +) + +cc_binary( name = "memutil_benchmark", + testonly = True, srcs = [ "internal/memutil.h", "internal/memutil_benchmark.cc", @@ -281,7 +298,6 @@ cc_test( ":strings", "//absl/base:core_headers", "@google_benchmark//:benchmark_main", - "@googletest//:gtest", ], ) @@ -332,8 +348,9 @@ cc_test( ], ) -cc_test( +cc_binary( name = "string_view_benchmark", + testonly = True, srcs = ["string_view_benchmark.cc"], copts = ABSL_TEST_COPTS, tags = ["benchmark"], @@ -344,7 +361,6 @@ cc_test( "//absl/base:core_headers", "//absl/base:raw_logging_internal", "@google_benchmark//:benchmark_main", - "@googletest//:gtest", ], ) @@ -365,9 +381,9 @@ cc_test( ], ) -cc_test( +cc_binary( name = "charset_benchmark", - size = "small", + testonly = True, srcs = [ "charset_benchmark.cc", ], @@ -380,7 +396,6 @@ cc_test( ":charset", "//absl/log:check", "@google_benchmark//:benchmark_main", - "@googletest//:gtest", ], ) @@ -928,7 +943,6 @@ cc_test( srcs = ["cordz_test.cc"], copts = ABSL_TEST_COPTS, tags = [ - "benchmark", "no_test_android_arm", "no_test_android_arm64", "no_test_android_x86", @@ -970,8 +984,25 @@ cc_test( ], ) -cc_test( +cc_binary( + name = "substitute_benchmark", + testonly = True, + srcs = ["substitute_benchmark.cc"], + copts = ABSL_TEST_COPTS, + tags = [ + "benchmark", + ], + visibility = ["//visibility:private"], + deps = [ + ":strings", + "//absl/base:core_headers", + "@google_benchmark//:benchmark_main", + ], +) + +cc_binary( name = "str_replace_benchmark", + testonly = True, srcs = ["str_replace_benchmark.cc"], copts = ABSL_TEST_COPTS, tags = ["benchmark"], @@ -980,7 +1011,6 @@ cc_test( ":strings", "//absl/base:raw_logging_internal", "@google_benchmark//:benchmark_main", - "@googletest//:gtest", ], ) @@ -1014,8 +1044,9 @@ cc_test( ], ) -cc_test( +cc_binary( name = "str_split_benchmark", + testonly = True, srcs = ["str_split_benchmark.cc"], copts = ABSL_TEST_COPTS, tags = ["benchmark"], @@ -1024,7 +1055,6 @@ cc_test( ":strings", "//absl/base:raw_logging_internal", "@google_benchmark//:benchmark_main", - "@googletest//:gtest", ], ) @@ -1041,8 +1071,9 @@ cc_test( ], ) -cc_test( +cc_binary( name = "ostringstream_benchmark", + testonly = True, srcs = ["internal/ostringstream_benchmark.cc"], copts = ABSL_TEST_COPTS, tags = ["benchmark"], @@ -1050,7 +1081,6 @@ cc_test( deps = [ ":internal", "@google_benchmark//:benchmark_main", - "@googletest//:gtest", ], ) @@ -1086,8 +1116,9 @@ cc_test( ], ) -cc_test( +cc_binary( name = "str_join_benchmark", + testonly = True, srcs = ["str_join_benchmark.cc"], copts = ABSL_TEST_COPTS, tags = ["benchmark"], @@ -1095,7 +1126,6 @@ cc_test( deps = [ ":strings", "@google_benchmark//:benchmark_main", - "@googletest//:gtest", ], ) @@ -1114,18 +1144,19 @@ cc_test( ], ) -cc_test( +cc_binary( name = "str_cat_benchmark", + testonly = True, srcs = ["str_cat_benchmark.cc"], copts = ABSL_TEST_COPTS, tags = ["benchmark"], visibility = ["//visibility:private"], deps = [ + ":str_format", ":strings", "//absl/random", "//absl/random:distributions", "@google_benchmark//:benchmark_main", - "@googletest//:gtest", ], ) @@ -1152,8 +1183,9 @@ cc_test( ], ) -cc_test( +cc_binary( name = "numbers_benchmark", + testonly = True, srcs = ["numbers_benchmark.cc"], copts = ABSL_TEST_COPTS, tags = ["benchmark"], @@ -1164,7 +1196,6 @@ cc_test( "//absl/random", "//absl/random:distributions", "@google_benchmark//:benchmark_main", - "@googletest//:gtest", ], ) @@ -1226,8 +1257,9 @@ cc_test( ], ) -cc_test( +cc_binary( name = "charconv_benchmark", + testonly = True, srcs = [ "charconv_benchmark.cc", ], @@ -1237,7 +1269,6 @@ cc_test( deps = [ ":strings", "@google_benchmark//:benchmark_main", - "@googletest//:gtest", ], ) diff --git a/absl/strings/ascii_benchmark.cc b/absl/strings/ascii_benchmark.cc index e4d01962..a839019c 100644 --- a/absl/strings/ascii_benchmark.cc +++ b/absl/strings/ascii_benchmark.cc @@ -12,15 +12,14 @@ // See the License for the specific language governing permissions and // limitations under the License. -#include "absl/strings/ascii.h" - #include +#include #include #include -#include -#include #include +#include +#include "absl/strings/ascii.h" #include "benchmark/benchmark.h" namespace { diff --git a/absl/strings/charconv_benchmark.cc b/absl/strings/charconv_benchmark.cc index e8c7371d..0ee9363d 100644 --- a/absl/strings/charconv_benchmark.cc +++ b/absl/strings/charconv_benchmark.cc @@ -12,12 +12,11 @@ // See the License for the specific language governing permissions and // limitations under the License. -#include "absl/strings/charconv.h" - #include #include #include +#include "absl/strings/charconv.h" #include "benchmark/benchmark.h" namespace { diff --git a/absl/strings/charset_benchmark.cc b/absl/strings/charset_benchmark.cc index bf7ae560..71339855 100644 --- a/absl/strings/charset_benchmark.cc +++ b/absl/strings/charset_benchmark.cc @@ -14,9 +14,9 @@ #include -#include "benchmark/benchmark.h" #include "absl/log/check.h" #include "absl/strings/charset.h" +#include "benchmark/benchmark.h" namespace { diff --git a/absl/strings/escaping_benchmark.cc b/absl/strings/escaping_benchmark.cc index 342fd142..32b8f6e0 100644 --- a/absl/strings/escaping_benchmark.cc +++ b/absl/strings/escaping_benchmark.cc @@ -12,18 +12,17 @@ // See the License for the specific language governing permissions and // limitations under the License. -#include "absl/strings/escaping.h" - #include #include #include #include -#include "benchmark/benchmark.h" #include "absl/base/internal/raw_logging.h" +#include "absl/strings/escaping.h" #include "absl/strings/internal/escaping_test_common.h" #include "absl/strings/str_cat.h" #include "absl/strings/string_view.h" +#include "benchmark/benchmark.h" namespace { diff --git a/absl/strings/internal/damerau_levenshtein_distance_benchmark.cc b/absl/strings/internal/damerau_levenshtein_distance_benchmark.cc new file mode 100644 index 00000000..76d6db47 --- /dev/null +++ b/absl/strings/internal/damerau_levenshtein_distance_benchmark.cc @@ -0,0 +1,56 @@ +// Copyright 2022 The Abseil Authors. +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +#include + +#include "absl/strings/internal/damerau_levenshtein_distance.h" +#include "benchmark/benchmark.h" + +namespace { + +std::string MakeTestString(int desired_length, int num_edits) { + std::string test(desired_length, 'x'); + for (int i = 0; (i < num_edits) && (i * 8 < desired_length); ++i) { + test[i * 8] = 'y'; + } + return test; +} + +void BenchmarkArgs(benchmark::internal::Benchmark* benchmark) { + // Each column is 8 bytes. + const auto string_size = {1, 8, 64, 100}; + const auto num_edits = {1, 2, 16, 16, 64, 80}; + const auto distance_cap = {1, 2, 3, 16, 64, 80}; + for (const int s : string_size) { + for (const int n : num_edits) { + for (const int d : distance_cap) { + if (n > s) continue; + benchmark->Args({s, n, d}); + } + } + } +} + +using absl::strings_internal::CappedDamerauLevenshteinDistance; +void BM_Distance(benchmark::State& state) { + std::string s1 = MakeTestString(state.range(0), 0); + std::string s2 = MakeTestString(state.range(0), state.range(1)); + const size_t cap = state.range(2); + for (auto _ : state) { + CappedDamerauLevenshteinDistance(s1, s2, cap); + } +} +BENCHMARK(BM_Distance)->Apply(BenchmarkArgs); + +} // namespace diff --git a/absl/strings/internal/memutil_benchmark.cc b/absl/strings/internal/memutil_benchmark.cc index 61e323a4..1186752c 100644 --- a/absl/strings/internal/memutil_benchmark.cc +++ b/absl/strings/internal/memutil_benchmark.cc @@ -12,13 +12,12 @@ // See the License for the specific language governing permissions and // limitations under the License. -#include "absl/strings/internal/memutil.h" - #include #include -#include "benchmark/benchmark.h" #include "absl/strings/ascii.h" +#include "absl/strings/internal/memutil.h" +#include "benchmark/benchmark.h" // We fill the haystack with aaaaaaaaaaaaaaaaaa...aaaab. // That gives us: diff --git a/absl/strings/internal/ostringstream_benchmark.cc b/absl/strings/internal/ostringstream_benchmark.cc index 5979f182..a95cf4d8 100644 --- a/absl/strings/internal/ostringstream_benchmark.cc +++ b/absl/strings/internal/ostringstream_benchmark.cc @@ -12,11 +12,10 @@ // See the License for the specific language governing permissions and // limitations under the License. -#include "absl/strings/internal/ostringstream.h" - #include #include +#include "absl/strings/internal/ostringstream.h" #include "benchmark/benchmark.h" namespace { diff --git a/absl/strings/numbers_benchmark.cc b/absl/strings/numbers_benchmark.cc index e7cb60a4..c58f8619 100644 --- a/absl/strings/numbers_benchmark.cc +++ b/absl/strings/numbers_benchmark.cc @@ -19,12 +19,12 @@ #include #include -#include "benchmark/benchmark.h" #include "absl/base/internal/raw_logging.h" #include "absl/random/distributions.h" #include "absl/random/random.h" #include "absl/strings/numbers.h" #include "absl/strings/string_view.h" +#include "benchmark/benchmark.h" namespace { diff --git a/absl/strings/str_cat_benchmark.cc b/absl/strings/str_cat_benchmark.cc index 0a851e7b..7695e8fb 100644 --- a/absl/strings/str_cat_benchmark.cc +++ b/absl/strings/str_cat_benchmark.cc @@ -21,12 +21,13 @@ #include #include -#include "benchmark/benchmark.h" #include "absl/random/log_uniform_int_distribution.h" #include "absl/random/random.h" #include "absl/strings/str_cat.h" +#include "absl/strings/str_format.h" #include "absl/strings/string_view.h" #include "absl/strings/substitute.h" +#include "benchmark/benchmark.h" namespace { @@ -111,6 +112,17 @@ void BM_HexCat_By_StrCat(benchmark::State& state) { } BENCHMARK(BM_HexCat_By_StrCat); +void BM_HexCat_By_StrFormat(benchmark::State& state) { + int i = 0; + for (auto _ : state) { + std::string result = + absl::StrFormat("%s %x", kStringOne, int64_t{i} + 0x10000000); + benchmark::DoNotOptimize(result); + i = IncrementAlternatingSign(i); + } +} +BENCHMARK(BM_HexCat_By_StrFormat); + void BM_HexCat_By_Substitute(benchmark::State& state) { int i = 0; for (auto _ : state) { @@ -145,6 +157,18 @@ void BM_DoubleToString_By_SixDigits(benchmark::State& state) { } BENCHMARK(BM_DoubleToString_By_SixDigits); +void BM_FloatToString_By_StrFormat(benchmark::State& state) { + int i = 0; + float foo = 0.0f; + for (auto _ : state) { + std::string result = + absl::StrFormat("%f != %lld", foo += 1.001f, int64_t{i}); + benchmark::DoNotOptimize(result); + i = IncrementAlternatingSign(i); + } +} +BENCHMARK(BM_FloatToString_By_StrFormat); + template void BM_StrAppendImpl(benchmark::State& state, Table table, size_t total_bytes, std::index_sequence) { diff --git a/absl/strings/str_join_benchmark.cc b/absl/strings/str_join_benchmark.cc index be7a7257..ffe6696a 100644 --- a/absl/strings/str_join_benchmark.cc +++ b/absl/strings/str_join_benchmark.cc @@ -13,13 +13,12 @@ // See the License for the specific language governing permissions and // limitations under the License. -#include "absl/strings/str_join.h" - #include #include -#include #include +#include +#include "absl/strings/str_join.h" #include "benchmark/benchmark.h" namespace { diff --git a/absl/strings/str_replace_benchmark.cc b/absl/strings/str_replace_benchmark.cc index 01331da2..cbe75721 100644 --- a/absl/strings/str_replace_benchmark.cc +++ b/absl/strings/str_replace_benchmark.cc @@ -12,13 +12,12 @@ // See the License for the specific language governing permissions and // limitations under the License. -#include "absl/strings/str_replace.h" - #include #include -#include "benchmark/benchmark.h" #include "absl/base/internal/raw_logging.h" +#include "absl/strings/str_replace.h" +#include "benchmark/benchmark.h" namespace { diff --git a/absl/strings/str_split_benchmark.cc b/absl/strings/str_split_benchmark.cc index 003a66b5..5a2e9530 100644 --- a/absl/strings/str_split_benchmark.cc +++ b/absl/strings/str_split_benchmark.cc @@ -12,8 +12,6 @@ // See the License for the specific language governing permissions and // limitations under the License. -#include "absl/strings/str_split.h" - #include #include #include @@ -21,9 +19,10 @@ #include #include -#include "benchmark/benchmark.h" #include "absl/base/internal/raw_logging.h" +#include "absl/strings/str_split.h" #include "absl/strings/string_view.h" +#include "benchmark/benchmark.h" namespace { diff --git a/absl/strings/string_view_benchmark.cc b/absl/strings/string_view_benchmark.cc index 98f747ca..4e36687f 100644 --- a/absl/strings/string_view_benchmark.cc +++ b/absl/strings/string_view_benchmark.cc @@ -12,8 +12,6 @@ // See the License for the specific language governing permissions and // limitations under the License. -#include "absl/strings/string_view.h" - #include #include #include @@ -23,11 +21,12 @@ #include #include -#include "benchmark/benchmark.h" #include "absl/base/attributes.h" #include "absl/base/internal/raw_logging.h" #include "absl/base/macros.h" #include "absl/strings/str_cat.h" +#include "absl/strings/string_view.h" +#include "benchmark/benchmark.h" namespace { diff --git a/absl/strings/substitute_benchmark.cc b/absl/strings/substitute_benchmark.cc new file mode 100644 index 00000000..e58ec867 --- /dev/null +++ b/absl/strings/substitute_benchmark.cc @@ -0,0 +1,158 @@ +// Copyright 2020 The Abseil Authors. +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +#include +#include +#include + +#include "absl/strings/str_cat.h" +#include "absl/strings/substitute.h" +#include "benchmark/benchmark.h" + +namespace { + +void BM_Substitute(benchmark::State& state) { + std::string s(state.range(0), 'x'); + int64_t bytes = 0; + for (auto _ : state) { + std::string result = absl::Substitute("$0 $1 $2 $3 $4 $5 $6 $7 $8 $9 $$", s, + s, s, s, s, s, s, s, s, s); + bytes += result.size(); + } + state.SetBytesProcessed(bytes); +} +BENCHMARK(BM_Substitute)->Range(0, 1024); + +// Like BM_Substitute, but use char* strings (which must then be copied +// to STL strings) for all parameters. This demonstrates that it is faster +// to use absl::Substitute() even if your inputs are char* strings. +void BM_SubstituteCstr(benchmark::State& state) { + std::string s(state.range(0), 'x'); + int64_t bytes = 0; + for (auto _ : state) { + std::string result = + absl::Substitute("$0 $1 $2 $3 $4 $5 $6 $7 $8 $9 $$", s.c_str(), + s.c_str(), s.c_str(), s.c_str(), s.c_str(), s.c_str(), + s.c_str(), s.c_str(), s.c_str(), s.c_str()); + bytes += result.size(); + } + state.SetBytesProcessed(bytes); +} +BENCHMARK(BM_SubstituteCstr)->Range(0, 1024); + +// For comparison with BM_Substitute. +void BM_StringPrintf(benchmark::State& state) { + std::string s(state.range(0), 'x'); + int64_t bytes = 0; + for (auto _ : state) { + std::string result = absl::StrCat(s, " ", s, " ", s, " ", s, " ", s, " ", s, + " ", s, " ", s, " ", s, " ", s); + bytes += result.size(); + } + state.SetBytesProcessed(bytes); +} +BENCHMARK(BM_StringPrintf)->Range(0, 1024); + +// Benchmark using absl::Substitute() together with SimpleItoa() to print +// numbers. This demonstrates that absl::Substitute() is faster than +// StringPrintf() even when the inputs are numbers. +void BM_SubstituteNumber(benchmark::State& state) { + const int n = state.range(0); + int64_t bytes = 0; + for (auto _ : state) { + std::string result = + absl::Substitute("$0 $1 $2 $3 $4 $5 $6 $7 $8 $9 $$", n, n + 1, n + 2, + n + 3, n + 4, n + 5, n + 6, n + 7, n + 8, n + 9); + bytes += result.size(); + } + state.SetBytesProcessed(bytes); +} +BENCHMARK(BM_SubstituteNumber)->Arg(0)->Arg(1 << 20); + +// For comparison with BM_SubstituteNumber. +void BM_StrCatNumber(benchmark::State& state) { + const int n = state.range(0); + int64_t bytes = 0; + for (auto _ : state) { + std::string result = + absl::StrCat(n, " ", n + 1, " ", n + 2, " ", n + 3, " ", n + 4, " ", + n + 5, " ", n + 6, " ", n + 7, " ", n + 8, " ", n + 9); + bytes += result.size(); + } + state.SetBytesProcessed(bytes); +} +BENCHMARK(BM_StrCatNumber)->Arg(0)->Arg(1 << 20); + +// Benchmark using absl::Substitute() with a single substitution, to test the +// speed at which it copies simple text. Even in this case, it's faster +// that StringPrintf(). +void BM_SubstituteSimpleText(benchmark::State& state) { + std::string s(state.range(0), 'x'); + int64_t bytes = 0; + for (auto _ : state) { + std::string result = absl::Substitute("$0", s.c_str()); + bytes += result.size(); + } + state.SetBytesProcessed(bytes); +} +BENCHMARK(BM_SubstituteSimpleText)->Range(0, 1024); + +// For comparison with BM_SubstituteSimpleText. +void BM_StrCatSimpleText(benchmark::State& state) { + std::string s(state.range(0), 'x'); + int64_t bytes = 0; + for (auto _ : state) { + std::string result = absl::StrCat("", s); + bytes += result.size(); + } + state.SetBytesProcessed(bytes); +} +BENCHMARK(BM_StrCatSimpleText)->Range(0, 1024); + +std::string MakeFormatByDensity(int density, bool subs_mode) { + std::string format((2 + density) * 10, 'x'); + for (size_t i = 0; i < 10; ++i) { + format[density * i] = subs_mode ? '$' : '%'; + format[density * i + 1] = subs_mode ? ('0' + i) : 's'; + } + return format; +} + +void BM_SubstituteDensity(benchmark::State& state) { + const std::string s(10, 'x'); + const std::string format = MakeFormatByDensity(state.range(0), true); + int64_t bytes = 0; + for (auto _ : state) { + std::string result = absl::Substitute(format, s, s, s, s, s, s, s, s, s, s); + bytes += result.size(); + } + state.SetBytesProcessed(bytes); +} +BENCHMARK(BM_SubstituteDensity)->Range(0, 256); + +void BM_StrCatDensity(benchmark::State& state) { + const std::string s(10, 'x'); + const std::string format(state.range(0), 'x'); + int64_t bytes = 0; + for (auto _ : state) { + std::string result = + absl::StrCat(s, format, s, format, s, format, s, format, s, format, s, + format, s, format, s, format, s, format, s, format); + bytes += result.size(); + } + state.SetBytesProcessed(bytes); +} +BENCHMARK(BM_StrCatDensity)->Range(0, 256); + +} // namespace diff --git a/absl/synchronization/BUILD.bazel b/absl/synchronization/BUILD.bazel index 867e9866..9b016033 100644 --- a/absl/synchronization/BUILD.bazel +++ b/absl/synchronization/BUILD.bazel @@ -230,7 +230,6 @@ cc_test( ":graphcycles_internal", "//absl/base:raw_logging_internal", "@google_benchmark//:benchmark_main", - "@googletest//:gtest", ], ) diff --git a/absl/synchronization/internal/graphcycles_benchmark.cc b/absl/synchronization/internal/graphcycles_benchmark.cc index 54823e0b..9012801f 100644 --- a/absl/synchronization/internal/graphcycles_benchmark.cc +++ b/absl/synchronization/internal/graphcycles_benchmark.cc @@ -12,14 +12,13 @@ // See the License for the specific language governing permissions and // limitations under the License. -#include "absl/synchronization/internal/graphcycles.h" - #include #include #include -#include "benchmark/benchmark.h" #include "absl/base/internal/raw_logging.h" +#include "absl/synchronization/internal/graphcycles.h" +#include "benchmark/benchmark.h" namespace { diff --git a/absl/time/BUILD.bazel b/absl/time/BUILD.bazel index b577d92d..445bdcc7 100644 --- a/absl/time/BUILD.bazel +++ b/absl/time/BUILD.bazel @@ -131,8 +131,9 @@ cc_test( ], ) -cc_test( +cc_binary( name = "time_benchmark", + testonly = True, srcs = [ "civil_time_benchmark.cc", "clock_benchmark.cc",