aboutsummaryrefslogtreecommitdiffstats
path: root/contrib/restricted/abseil-cpp-tstring/y_absl/strings/str_cat.h
diff options
context:
space:
mode:
authoranastasy888 <anastasy888@yandex-team.ru>2022-02-10 16:45:54 +0300
committerDaniil Cherednik <dcherednik@yandex-team.ru>2022-02-10 16:45:54 +0300
commit49f765d71da452ea93138a25559dfa68dd76c7f3 (patch)
tree1016041feb637349e401dcc0fa85217dd2c2c639 /contrib/restricted/abseil-cpp-tstring/y_absl/strings/str_cat.h
parent7353a3fdea9c67c256980c00a2b3b67f09b23a27 (diff)
downloadydb-49f765d71da452ea93138a25559dfa68dd76c7f3.tar.gz
Restoring authorship annotation for <anastasy888@yandex-team.ru>. Commit 1 of 2.
Diffstat (limited to 'contrib/restricted/abseil-cpp-tstring/y_absl/strings/str_cat.h')
-rw-r--r--contrib/restricted/abseil-cpp-tstring/y_absl/strings/str_cat.h716
1 files changed, 358 insertions, 358 deletions
diff --git a/contrib/restricted/abseil-cpp-tstring/y_absl/strings/str_cat.h b/contrib/restricted/abseil-cpp-tstring/y_absl/strings/str_cat.h
index a77c9ae906..29c50dd4f7 100644
--- a/contrib/restricted/abseil-cpp-tstring/y_absl/strings/str_cat.h
+++ b/contrib/restricted/abseil-cpp-tstring/y_absl/strings/str_cat.h
@@ -1,411 +1,411 @@
-//
-// Copyright 2017 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.
-//
-// -----------------------------------------------------------------------------
-// File: str_cat.h
-// -----------------------------------------------------------------------------
-//
-// This package contains functions for efficiently concatenating and appending
-// strings: `StrCat()` and `StrAppend()`. Most of the work within these routines
-// is actually handled through use of a special AlphaNum type, which was
-// designed to be used as a parameter type that efficiently manages conversion
-// to strings and avoids copies in the above operations.
-//
-// Any routine accepting either a string or a number may accept `AlphaNum`.
-// The basic idea is that by accepting a `const AlphaNum &` as an argument
-// to your function, your callers will automagically convert bools, integers,
-// and floating point values to strings for you.
-//
+//
+// Copyright 2017 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.
+//
+// -----------------------------------------------------------------------------
+// File: str_cat.h
+// -----------------------------------------------------------------------------
+//
+// This package contains functions for efficiently concatenating and appending
+// strings: `StrCat()` and `StrAppend()`. Most of the work within these routines
+// is actually handled through use of a special AlphaNum type, which was
+// designed to be used as a parameter type that efficiently manages conversion
+// to strings and avoids copies in the above operations.
+//
+// Any routine accepting either a string or a number may accept `AlphaNum`.
+// The basic idea is that by accepting a `const AlphaNum &` as an argument
+// to your function, your callers will automagically convert bools, integers,
+// and floating point values to strings for you.
+//
// NOTE: Use of `AlphaNum` outside of the //y_absl/strings package is unsupported
-// except for the specific case of function parameters of type `AlphaNum` or
-// `const AlphaNum &`. In particular, instantiating `AlphaNum` directly as a
-// stack variable is not supported.
-//
-// Conversion from 8-bit values is not accepted because, if it were, then an
-// attempt to pass ':' instead of ":" might result in a 58 ending up in your
-// result.
-//
-// Bools convert to "0" or "1". Pointers to types other than `char *` are not
-// valid inputs. No output is generated for null `char *` pointers.
-//
-// Floating point numbers are formatted with six-digit precision, which is
-// the default for "std::cout <<" or printf "%g" (the same as "%.6g").
-//
-// You can convert to hexadecimal output rather than decimal output using the
-// `Hex` type contained here. To do so, pass `Hex(my_int)` as a parameter to
-// `StrCat()` or `StrAppend()`. You may specify a minimum hex field width using
-// a `PadSpec` enum.
-//
-// -----------------------------------------------------------------------------
-
-#ifndef ABSL_STRINGS_STR_CAT_H_
-#define ABSL_STRINGS_STR_CAT_H_
-
-#include <array>
-#include <cstdint>
+// except for the specific case of function parameters of type `AlphaNum` or
+// `const AlphaNum &`. In particular, instantiating `AlphaNum` directly as a
+// stack variable is not supported.
+//
+// Conversion from 8-bit values is not accepted because, if it were, then an
+// attempt to pass ':' instead of ":" might result in a 58 ending up in your
+// result.
+//
+// Bools convert to "0" or "1". Pointers to types other than `char *` are not
+// valid inputs. No output is generated for null `char *` pointers.
+//
+// Floating point numbers are formatted with six-digit precision, which is
+// the default for "std::cout <<" or printf "%g" (the same as "%.6g").
+//
+// You can convert to hexadecimal output rather than decimal output using the
+// `Hex` type contained here. To do so, pass `Hex(my_int)` as a parameter to
+// `StrCat()` or `StrAppend()`. You may specify a minimum hex field width using
+// a `PadSpec` enum.
+//
+// -----------------------------------------------------------------------------
+
+#ifndef ABSL_STRINGS_STR_CAT_H_
+#define ABSL_STRINGS_STR_CAT_H_
+
+#include <array>
+#include <cstdint>
#include <util/generic/string.h>
-#include <type_traits>
-#include <vector>
-
+#include <type_traits>
+#include <vector>
+
#include "y_absl/base/port.h"
#include "y_absl/strings/numbers.h"
#include "y_absl/strings/string_view.h"
-
+
namespace y_absl {
ABSL_NAMESPACE_BEGIN
-
-namespace strings_internal {
-// AlphaNumBuffer allows a way to pass a string to StrCat without having to do
-// memory allocation. It is simply a pair of a fixed-size character array, and
+
+namespace strings_internal {
+// AlphaNumBuffer allows a way to pass a string to StrCat without having to do
+// memory allocation. It is simply a pair of a fixed-size character array, and
// a size. Please don't use outside of y_absl, yet.
-template <size_t max_size>
-struct AlphaNumBuffer {
- std::array<char, max_size> data;
- size_t size;
-};
-
-} // namespace strings_internal
-
-// Enum that specifies the number of significant digits to return in a `Hex` or
-// `Dec` conversion and fill character to use. A `kZeroPad2` value, for example,
-// would produce hexadecimal strings such as "0a","0f" and a 'kSpacePad5' value
-// would produce hexadecimal strings such as " a"," f".
-enum PadSpec : uint8_t {
- kNoPad = 1,
- kZeroPad2,
- kZeroPad3,
- kZeroPad4,
- kZeroPad5,
- kZeroPad6,
- kZeroPad7,
- kZeroPad8,
- kZeroPad9,
- kZeroPad10,
- kZeroPad11,
- kZeroPad12,
- kZeroPad13,
- kZeroPad14,
- kZeroPad15,
- kZeroPad16,
- kZeroPad17,
- kZeroPad18,
- kZeroPad19,
- kZeroPad20,
-
- kSpacePad2 = kZeroPad2 + 64,
- kSpacePad3,
- kSpacePad4,
- kSpacePad5,
- kSpacePad6,
- kSpacePad7,
- kSpacePad8,
- kSpacePad9,
- kSpacePad10,
- kSpacePad11,
- kSpacePad12,
- kSpacePad13,
- kSpacePad14,
- kSpacePad15,
- kSpacePad16,
- kSpacePad17,
- kSpacePad18,
- kSpacePad19,
- kSpacePad20,
-};
-
-// -----------------------------------------------------------------------------
-// Hex
-// -----------------------------------------------------------------------------
-//
-// `Hex` stores a set of hexadecimal string conversion parameters for use
-// within `AlphaNum` string conversions.
-struct Hex {
- uint64_t value;
- uint8_t width;
- char fill;
-
- template <typename Int>
- explicit Hex(
+template <size_t max_size>
+struct AlphaNumBuffer {
+ std::array<char, max_size> data;
+ size_t size;
+};
+
+} // namespace strings_internal
+
+// Enum that specifies the number of significant digits to return in a `Hex` or
+// `Dec` conversion and fill character to use. A `kZeroPad2` value, for example,
+// would produce hexadecimal strings such as "0a","0f" and a 'kSpacePad5' value
+// would produce hexadecimal strings such as " a"," f".
+enum PadSpec : uint8_t {
+ kNoPad = 1,
+ kZeroPad2,
+ kZeroPad3,
+ kZeroPad4,
+ kZeroPad5,
+ kZeroPad6,
+ kZeroPad7,
+ kZeroPad8,
+ kZeroPad9,
+ kZeroPad10,
+ kZeroPad11,
+ kZeroPad12,
+ kZeroPad13,
+ kZeroPad14,
+ kZeroPad15,
+ kZeroPad16,
+ kZeroPad17,
+ kZeroPad18,
+ kZeroPad19,
+ kZeroPad20,
+
+ kSpacePad2 = kZeroPad2 + 64,
+ kSpacePad3,
+ kSpacePad4,
+ kSpacePad5,
+ kSpacePad6,
+ kSpacePad7,
+ kSpacePad8,
+ kSpacePad9,
+ kSpacePad10,
+ kSpacePad11,
+ kSpacePad12,
+ kSpacePad13,
+ kSpacePad14,
+ kSpacePad15,
+ kSpacePad16,
+ kSpacePad17,
+ kSpacePad18,
+ kSpacePad19,
+ kSpacePad20,
+};
+
+// -----------------------------------------------------------------------------
+// Hex
+// -----------------------------------------------------------------------------
+//
+// `Hex` stores a set of hexadecimal string conversion parameters for use
+// within `AlphaNum` string conversions.
+struct Hex {
+ uint64_t value;
+ uint8_t width;
+ char fill;
+
+ template <typename Int>
+ explicit Hex(
Int v, PadSpec spec = y_absl::kNoPad,
- typename std::enable_if<sizeof(Int) == 1 &&
- !std::is_pointer<Int>::value>::type* = nullptr)
- : Hex(spec, static_cast<uint8_t>(v)) {}
- template <typename Int>
- explicit Hex(
+ typename std::enable_if<sizeof(Int) == 1 &&
+ !std::is_pointer<Int>::value>::type* = nullptr)
+ : Hex(spec, static_cast<uint8_t>(v)) {}
+ template <typename Int>
+ explicit Hex(
Int v, PadSpec spec = y_absl::kNoPad,
- typename std::enable_if<sizeof(Int) == 2 &&
- !std::is_pointer<Int>::value>::type* = nullptr)
- : Hex(spec, static_cast<uint16_t>(v)) {}
- template <typename Int>
- explicit Hex(
+ typename std::enable_if<sizeof(Int) == 2 &&
+ !std::is_pointer<Int>::value>::type* = nullptr)
+ : Hex(spec, static_cast<uint16_t>(v)) {}
+ template <typename Int>
+ explicit Hex(
Int v, PadSpec spec = y_absl::kNoPad,
- typename std::enable_if<sizeof(Int) == 4 &&
- !std::is_pointer<Int>::value>::type* = nullptr)
- : Hex(spec, static_cast<uint32_t>(v)) {}
- template <typename Int>
- explicit Hex(
+ typename std::enable_if<sizeof(Int) == 4 &&
+ !std::is_pointer<Int>::value>::type* = nullptr)
+ : Hex(spec, static_cast<uint32_t>(v)) {}
+ template <typename Int>
+ explicit Hex(
Int v, PadSpec spec = y_absl::kNoPad,
- typename std::enable_if<sizeof(Int) == 8 &&
- !std::is_pointer<Int>::value>::type* = nullptr)
- : Hex(spec, static_cast<uint64_t>(v)) {}
- template <typename Pointee>
+ typename std::enable_if<sizeof(Int) == 8 &&
+ !std::is_pointer<Int>::value>::type* = nullptr)
+ : Hex(spec, static_cast<uint64_t>(v)) {}
+ template <typename Pointee>
explicit Hex(Pointee* v, PadSpec spec = y_absl::kNoPad)
- : Hex(spec, reinterpret_cast<uintptr_t>(v)) {}
-
- private:
- Hex(PadSpec spec, uint64_t v)
- : value(v),
+ : Hex(spec, reinterpret_cast<uintptr_t>(v)) {}
+
+ private:
+ Hex(PadSpec spec, uint64_t v)
+ : value(v),
width(spec == y_absl::kNoPad
- ? 1
+ ? 1
: spec >= y_absl::kSpacePad2 ? spec - y_absl::kSpacePad2 + 2
: spec - y_absl::kZeroPad2 + 2),
fill(spec >= y_absl::kSpacePad2 ? ' ' : '0') {}
-};
-
-// -----------------------------------------------------------------------------
-// Dec
-// -----------------------------------------------------------------------------
-//
-// `Dec` stores a set of decimal string conversion parameters for use
-// within `AlphaNum` string conversions. Dec is slower than the default
-// integer conversion, so use it only if you need padding.
-struct Dec {
- uint64_t value;
- uint8_t width;
- char fill;
- bool neg;
-
- template <typename Int>
+};
+
+// -----------------------------------------------------------------------------
+// Dec
+// -----------------------------------------------------------------------------
+//
+// `Dec` stores a set of decimal string conversion parameters for use
+// within `AlphaNum` string conversions. Dec is slower than the default
+// integer conversion, so use it only if you need padding.
+struct Dec {
+ uint64_t value;
+ uint8_t width;
+ char fill;
+ bool neg;
+
+ template <typename Int>
explicit Dec(Int v, PadSpec spec = y_absl::kNoPad,
- typename std::enable_if<(sizeof(Int) <= 8)>::type* = nullptr)
- : value(v >= 0 ? static_cast<uint64_t>(v)
- : uint64_t{0} - static_cast<uint64_t>(v)),
+ typename std::enable_if<(sizeof(Int) <= 8)>::type* = nullptr)
+ : value(v >= 0 ? static_cast<uint64_t>(v)
+ : uint64_t{0} - static_cast<uint64_t>(v)),
width(spec == y_absl::kNoPad
- ? 1
+ ? 1
: spec >= y_absl::kSpacePad2 ? spec - y_absl::kSpacePad2 + 2
: spec - y_absl::kZeroPad2 + 2),
fill(spec >= y_absl::kSpacePad2 ? ' ' : '0'),
- neg(v < 0) {}
-};
-
-// -----------------------------------------------------------------------------
-// AlphaNum
-// -----------------------------------------------------------------------------
-//
-// The `AlphaNum` class acts as the main parameter type for `StrCat()` and
-// `StrAppend()`, providing efficient conversion of numeric, boolean, and
-// hexadecimal values (through the `Hex` type) into strings.
-
-class AlphaNum {
- public:
- // No bool ctor -- bools convert to an integral type.
- // A bool ctor would also convert incoming pointers (bletch).
-
- AlphaNum(int x) // NOLINT(runtime/explicit)
- : piece_(digits_,
- numbers_internal::FastIntToBuffer(x, digits_) - &digits_[0]) {}
- AlphaNum(unsigned int x) // NOLINT(runtime/explicit)
- : piece_(digits_,
- numbers_internal::FastIntToBuffer(x, digits_) - &digits_[0]) {}
- AlphaNum(long x) // NOLINT(*)
- : piece_(digits_,
- numbers_internal::FastIntToBuffer(x, digits_) - &digits_[0]) {}
- AlphaNum(unsigned long x) // NOLINT(*)
- : piece_(digits_,
- numbers_internal::FastIntToBuffer(x, digits_) - &digits_[0]) {}
- AlphaNum(long long x) // NOLINT(*)
- : piece_(digits_,
- numbers_internal::FastIntToBuffer(x, digits_) - &digits_[0]) {}
- AlphaNum(unsigned long long x) // NOLINT(*)
- : piece_(digits_,
- numbers_internal::FastIntToBuffer(x, digits_) - &digits_[0]) {}
-
- AlphaNum(float f) // NOLINT(runtime/explicit)
- : piece_(digits_, numbers_internal::SixDigitsToBuffer(f, digits_)) {}
- AlphaNum(double f) // NOLINT(runtime/explicit)
- : piece_(digits_, numbers_internal::SixDigitsToBuffer(f, digits_)) {}
-
- AlphaNum(Hex hex); // NOLINT(runtime/explicit)
- AlphaNum(Dec dec); // NOLINT(runtime/explicit)
-
- template <size_t size>
- AlphaNum( // NOLINT(runtime/explicit)
- const strings_internal::AlphaNumBuffer<size>& buf)
- : piece_(&buf.data[0], buf.size) {}
-
- AlphaNum(const char* c_str) : piece_(c_str) {} // NOLINT(runtime/explicit)
+ neg(v < 0) {}
+};
+
+// -----------------------------------------------------------------------------
+// AlphaNum
+// -----------------------------------------------------------------------------
+//
+// The `AlphaNum` class acts as the main parameter type for `StrCat()` and
+// `StrAppend()`, providing efficient conversion of numeric, boolean, and
+// hexadecimal values (through the `Hex` type) into strings.
+
+class AlphaNum {
+ public:
+ // No bool ctor -- bools convert to an integral type.
+ // A bool ctor would also convert incoming pointers (bletch).
+
+ AlphaNum(int x) // NOLINT(runtime/explicit)
+ : piece_(digits_,
+ numbers_internal::FastIntToBuffer(x, digits_) - &digits_[0]) {}
+ AlphaNum(unsigned int x) // NOLINT(runtime/explicit)
+ : piece_(digits_,
+ numbers_internal::FastIntToBuffer(x, digits_) - &digits_[0]) {}
+ AlphaNum(long x) // NOLINT(*)
+ : piece_(digits_,
+ numbers_internal::FastIntToBuffer(x, digits_) - &digits_[0]) {}
+ AlphaNum(unsigned long x) // NOLINT(*)
+ : piece_(digits_,
+ numbers_internal::FastIntToBuffer(x, digits_) - &digits_[0]) {}
+ AlphaNum(long long x) // NOLINT(*)
+ : piece_(digits_,
+ numbers_internal::FastIntToBuffer(x, digits_) - &digits_[0]) {}
+ AlphaNum(unsigned long long x) // NOLINT(*)
+ : piece_(digits_,
+ numbers_internal::FastIntToBuffer(x, digits_) - &digits_[0]) {}
+
+ AlphaNum(float f) // NOLINT(runtime/explicit)
+ : piece_(digits_, numbers_internal::SixDigitsToBuffer(f, digits_)) {}
+ AlphaNum(double f) // NOLINT(runtime/explicit)
+ : piece_(digits_, numbers_internal::SixDigitsToBuffer(f, digits_)) {}
+
+ AlphaNum(Hex hex); // NOLINT(runtime/explicit)
+ AlphaNum(Dec dec); // NOLINT(runtime/explicit)
+
+ template <size_t size>
+ AlphaNum( // NOLINT(runtime/explicit)
+ const strings_internal::AlphaNumBuffer<size>& buf)
+ : piece_(&buf.data[0], buf.size) {}
+
+ AlphaNum(const char* c_str) : piece_(c_str) {} // NOLINT(runtime/explicit)
AlphaNum(y_absl::string_view pc) : piece_(pc) {} // NOLINT(runtime/explicit)
-
- template <typename Allocator>
- AlphaNum( // NOLINT(runtime/explicit)
- const std::basic_string<char, std::char_traits<char>, Allocator>& str)
- : piece_(str) {}
-
+
+ template <typename Allocator>
+ AlphaNum( // NOLINT(runtime/explicit)
+ const std::basic_string<char, std::char_traits<char>, Allocator>& str)
+ : piece_(str) {}
+
AlphaNum(const TString& str)
: piece_(str.data(), str.size()) {}
// Use string literals ":" instead of character literals ':'.
- AlphaNum(char c) = delete; // NOLINT(runtime/explicit)
-
- AlphaNum(const AlphaNum&) = delete;
- AlphaNum& operator=(const AlphaNum&) = delete;
-
+ AlphaNum(char c) = delete; // NOLINT(runtime/explicit)
+
+ AlphaNum(const AlphaNum&) = delete;
+ AlphaNum& operator=(const AlphaNum&) = delete;
+
y_absl::string_view::size_type size() const { return piece_.size(); }
- const char* data() const { return piece_.data(); }
+ const char* data() const { return piece_.data(); }
y_absl::string_view Piece() const { return piece_; }
-
- // Normal enums are already handled by the integer formatters.
- // This overload matches only scoped enums.
- template <typename T,
- typename = typename std::enable_if<
- std::is_enum<T>{} && !std::is_convertible<T, int>{}>::type>
- AlphaNum(T e) // NOLINT(runtime/explicit)
- : AlphaNum(static_cast<typename std::underlying_type<T>::type>(e)) {}
-
- // vector<bool>::reference and const_reference require special help to
- // convert to `AlphaNum` because it requires two user defined conversions.
- template <
- typename T,
- typename std::enable_if<
- std::is_class<T>::value &&
- (std::is_same<T, std::vector<bool>::reference>::value ||
- std::is_same<T, std::vector<bool>::const_reference>::value)>::type* =
- nullptr>
- AlphaNum(T e) : AlphaNum(static_cast<bool>(e)) {} // NOLINT(runtime/explicit)
-
- private:
+
+ // Normal enums are already handled by the integer formatters.
+ // This overload matches only scoped enums.
+ template <typename T,
+ typename = typename std::enable_if<
+ std::is_enum<T>{} && !std::is_convertible<T, int>{}>::type>
+ AlphaNum(T e) // NOLINT(runtime/explicit)
+ : AlphaNum(static_cast<typename std::underlying_type<T>::type>(e)) {}
+
+ // vector<bool>::reference and const_reference require special help to
+ // convert to `AlphaNum` because it requires two user defined conversions.
+ template <
+ typename T,
+ typename std::enable_if<
+ std::is_class<T>::value &&
+ (std::is_same<T, std::vector<bool>::reference>::value ||
+ std::is_same<T, std::vector<bool>::const_reference>::value)>::type* =
+ nullptr>
+ AlphaNum(T e) : AlphaNum(static_cast<bool>(e)) {} // NOLINT(runtime/explicit)
+
+ private:
y_absl::string_view piece_;
- char digits_[numbers_internal::kFastToBufferSize];
-};
-
-// -----------------------------------------------------------------------------
-// StrCat()
-// -----------------------------------------------------------------------------
-//
-// Merges given strings or numbers, using no delimiter(s), returning the merged
-// result as a string.
-//
-// `StrCat()` is designed to be the fastest possible way to construct a string
-// out of a mix of raw C strings, string_views, strings, bool values,
-// and numeric values.
-//
-// Don't use `StrCat()` for user-visible strings. The localization process
-// works poorly on strings built up out of fragments.
-//
-// For clarity and performance, don't use `StrCat()` when appending to a
-// string. Use `StrAppend()` instead. In particular, avoid using any of these
-// (anti-)patterns:
-//
-// str.append(StrCat(...))
-// str += StrCat(...)
-// str = StrCat(str, ...)
-//
-// The last case is the worst, with a potential to change a loop
-// from a linear time operation with O(1) dynamic allocations into a
-// quadratic time operation with O(n) dynamic allocations.
-//
-// See `StrAppend()` below for more information.
-
-namespace strings_internal {
-
-// Do not call directly - this is not part of the public API.
+ char digits_[numbers_internal::kFastToBufferSize];
+};
+
+// -----------------------------------------------------------------------------
+// StrCat()
+// -----------------------------------------------------------------------------
+//
+// Merges given strings or numbers, using no delimiter(s), returning the merged
+// result as a string.
+//
+// `StrCat()` is designed to be the fastest possible way to construct a string
+// out of a mix of raw C strings, string_views, strings, bool values,
+// and numeric values.
+//
+// Don't use `StrCat()` for user-visible strings. The localization process
+// works poorly on strings built up out of fragments.
+//
+// For clarity and performance, don't use `StrCat()` when appending to a
+// string. Use `StrAppend()` instead. In particular, avoid using any of these
+// (anti-)patterns:
+//
+// str.append(StrCat(...))
+// str += StrCat(...)
+// str = StrCat(str, ...)
+//
+// The last case is the worst, with a potential to change a loop
+// from a linear time operation with O(1) dynamic allocations into a
+// quadratic time operation with O(n) dynamic allocations.
+//
+// See `StrAppend()` below for more information.
+
+namespace strings_internal {
+
+// Do not call directly - this is not part of the public API.
TString CatPieces(std::initializer_list<y_absl::string_view> pieces);
void AppendPieces(TString* dest,
std::initializer_list<y_absl::string_view> pieces);
-
-} // namespace strings_internal
-
+
+} // namespace strings_internal
+
ABSL_MUST_USE_RESULT inline TString StrCat() { return TString(); }
-
+
ABSL_MUST_USE_RESULT inline TString StrCat(const AlphaNum& a) {
return TString(a.data(), a.size());
-}
-
+}
+
ABSL_MUST_USE_RESULT TString StrCat(const AlphaNum& a, const AlphaNum& b);
ABSL_MUST_USE_RESULT TString StrCat(const AlphaNum& a, const AlphaNum& b,
- const AlphaNum& c);
+ const AlphaNum& c);
ABSL_MUST_USE_RESULT TString StrCat(const AlphaNum& a, const AlphaNum& b,
- const AlphaNum& c, const AlphaNum& d);
-
-// Support 5 or more arguments
-template <typename... AV>
+ const AlphaNum& c, const AlphaNum& d);
+
+// Support 5 or more arguments
+template <typename... AV>
ABSL_MUST_USE_RESULT inline TString StrCat(
- const AlphaNum& a, const AlphaNum& b, const AlphaNum& c, const AlphaNum& d,
- const AlphaNum& e, const AV&... args) {
- return strings_internal::CatPieces(
- {a.Piece(), b.Piece(), c.Piece(), d.Piece(), e.Piece(),
- static_cast<const AlphaNum&>(args).Piece()...});
-}
-
-// -----------------------------------------------------------------------------
-// StrAppend()
-// -----------------------------------------------------------------------------
-//
-// Appends a string or set of strings to an existing string, in a similar
-// fashion to `StrCat()`.
-//
-// WARNING: `StrAppend(&str, a, b, c, ...)` requires that none of the
-// a, b, c, parameters be a reference into str. For speed, `StrAppend()` does
-// not try to check each of its input arguments to be sure that they are not
-// a subset of the string being appended to. That is, while this will work:
-//
+ const AlphaNum& a, const AlphaNum& b, const AlphaNum& c, const AlphaNum& d,
+ const AlphaNum& e, const AV&... args) {
+ return strings_internal::CatPieces(
+ {a.Piece(), b.Piece(), c.Piece(), d.Piece(), e.Piece(),
+ static_cast<const AlphaNum&>(args).Piece()...});
+}
+
+// -----------------------------------------------------------------------------
+// StrAppend()
+// -----------------------------------------------------------------------------
+//
+// Appends a string or set of strings to an existing string, in a similar
+// fashion to `StrCat()`.
+//
+// WARNING: `StrAppend(&str, a, b, c, ...)` requires that none of the
+// a, b, c, parameters be a reference into str. For speed, `StrAppend()` does
+// not try to check each of its input arguments to be sure that they are not
+// a subset of the string being appended to. That is, while this will work:
+//
// TString s = "foo";
-// s += s;
-//
-// This output is undefined:
-//
+// s += s;
+//
+// This output is undefined:
+//
// TString s = "foo";
-// StrAppend(&s, s);
-//
+// StrAppend(&s, s);
+//
// This output is undefined as well, since `y_absl::string_view` does not own its
-// data:
-//
+// data:
+//
// TString s = "foobar";
// y_absl::string_view p = s;
-// StrAppend(&s, p);
-
+// StrAppend(&s, p);
+
inline void StrAppend(TString*) {}
void StrAppend(TString* dest, const AlphaNum& a);
void StrAppend(TString* dest, const AlphaNum& a, const AlphaNum& b);
void StrAppend(TString* dest, const AlphaNum& a, const AlphaNum& b,
- const AlphaNum& c);
+ const AlphaNum& c);
void StrAppend(TString* dest, const AlphaNum& a, const AlphaNum& b,
- const AlphaNum& c, const AlphaNum& d);
-
-// Support 5 or more arguments
-template <typename... AV>
+ const AlphaNum& c, const AlphaNum& d);
+
+// Support 5 or more arguments
+template <typename... AV>
inline void StrAppend(TString* dest, const AlphaNum& a, const AlphaNum& b,
- const AlphaNum& c, const AlphaNum& d, const AlphaNum& e,
- const AV&... args) {
- strings_internal::AppendPieces(
- dest, {a.Piece(), b.Piece(), c.Piece(), d.Piece(), e.Piece(),
- static_cast<const AlphaNum&>(args).Piece()...});
-}
-
-// Helper function for the future StrCat default floating-point format, %.6g
-// This is fast.
-inline strings_internal::AlphaNumBuffer<
- numbers_internal::kSixDigitsToBufferSize>
-SixDigits(double d) {
- strings_internal::AlphaNumBuffer<numbers_internal::kSixDigitsToBufferSize>
- result;
- result.size = numbers_internal::SixDigitsToBuffer(d, &result.data[0]);
- return result;
-}
-
+ const AlphaNum& c, const AlphaNum& d, const AlphaNum& e,
+ const AV&... args) {
+ strings_internal::AppendPieces(
+ dest, {a.Piece(), b.Piece(), c.Piece(), d.Piece(), e.Piece(),
+ static_cast<const AlphaNum&>(args).Piece()...});
+}
+
+// Helper function for the future StrCat default floating-point format, %.6g
+// This is fast.
+inline strings_internal::AlphaNumBuffer<
+ numbers_internal::kSixDigitsToBufferSize>
+SixDigits(double d) {
+ strings_internal::AlphaNumBuffer<numbers_internal::kSixDigitsToBufferSize>
+ result;
+ result.size = numbers_internal::SixDigitsToBuffer(d, &result.data[0]);
+ return result;
+}
+
ABSL_NAMESPACE_END
} // namespace y_absl
-
-#endif // ABSL_STRINGS_STR_CAT_H_
+
+#endif // ABSL_STRINGS_STR_CAT_H_