about summary refs log tree commit diff
diff options
context:
space:
mode:
-rw-r--r--absl/container/BUILD.bazel3
-rw-r--r--absl/container/fixed_array.h18
-rw-r--r--absl/container/fixed_array_test.cc37
-rw-r--r--absl/strings/str_cat.h3
-rw-r--r--absl/strings/substitute.h14
5 files changed, 53 insertions, 22 deletions
diff --git a/absl/container/BUILD.bazel b/absl/container/BUILD.bazel
index 7d550cb16c5a..295f41250590 100644
--- a/absl/container/BUILD.bazel
+++ b/absl/container/BUILD.bazel
@@ -33,6 +33,7 @@ cc_library(
         "//absl/base:core_headers",
         "//absl/base:dynamic_annotations",
         "//absl/base:throw_delegate",
+        "//absl/memory",
     ],
 )
 
@@ -42,7 +43,6 @@ cc_test(
     copts = ABSL_TEST_COPTS + ["-fexceptions"],
     deps = [
         ":fixed_array",
-        "//absl/base:core_headers",
         "//absl/base:exception_testing",
         "//absl/memory",
         "@com_google_googletest//:gtest_main",
@@ -55,7 +55,6 @@ cc_test(
     copts = ABSL_TEST_COPTS,
     deps = [
         ":fixed_array",
-        "//absl/base:core_headers",
         "//absl/base:exception_testing",
         "//absl/memory",
         "@com_google_googletest//:gtest_main",
diff --git a/absl/container/fixed_array.h b/absl/container/fixed_array.h
index 58240b499a56..ec6fced16aba 100644
--- a/absl/container/fixed_array.h
+++ b/absl/container/fixed_array.h
@@ -47,6 +47,7 @@
 #include "absl/base/macros.h"
 #include "absl/base/optimization.h"
 #include "absl/base/port.h"
+#include "absl/memory/memory.h"
 
 namespace absl {
 
@@ -107,6 +108,15 @@ class FixedArray {
           ? kInlineBytesDefault / sizeof(value_type)
           : inlined;
 
+  FixedArray(const FixedArray& other) : rep_(other.begin(), other.end()) {}
+  FixedArray(FixedArray&& other) noexcept(
+  // clang-format off
+      absl::allocator_is_nothrow<std::allocator<value_type>>::value &&
+  // clang-format on
+          std::is_nothrow_move_constructible<value_type>::value)
+      : rep_(std::make_move_iterator(other.begin()),
+             std::make_move_iterator(other.end())) {}
+
   // Creates an array object that can store `n` elements.
   // Note that trivially constructible elements will be uninitialized.
   explicit FixedArray(size_type n) : rep_(n) {}
@@ -126,11 +136,9 @@ class FixedArray {
 
   ~FixedArray() {}
 
-  // Copy and move construction and assignment are deleted because (1) you can't
-  // copy or move an array, (2) assignment breaks the invariant that the size of
-  // a `FixedArray` never changes, and (3) there's no clear answer as to what
-  // should happen to a moved-from `FixedArray`.
-  FixedArray(const FixedArray&) = delete;
+  // Assignments are deleted because they break the invariant that the size of a
+  // `FixedArray` never changes.
+  void operator=(FixedArray&&) = delete;
   void operator=(const FixedArray&) = delete;
 
   // FixedArray::size()
diff --git a/absl/container/fixed_array_test.cc b/absl/container/fixed_array_test.cc
index 9e88eab0c696..b6782f517a6c 100644
--- a/absl/container/fixed_array_test.cc
+++ b/absl/container/fixed_array_test.cc
@@ -27,6 +27,8 @@
 #include "absl/base/internal/exception_testing.h"
 #include "absl/memory/memory.h"
 
+using ::testing::ElementsAreArray;
+
 namespace {
 
 // Helper routine to determine if a absl::FixedArray used stack allocation.
@@ -89,6 +91,41 @@ class ThreeInts {
 
 int ThreeInts::counter = 0;
 
+TEST(FixedArrayTest, CopyCtor) {
+  absl::FixedArray<int, 10> on_stack(5);
+  std::iota(on_stack.begin(), on_stack.end(), 0);
+  absl::FixedArray<int, 10> stack_copy = on_stack;
+  EXPECT_THAT(stack_copy, ElementsAreArray(on_stack));
+  EXPECT_TRUE(IsOnStack(stack_copy));
+
+  absl::FixedArray<int, 10> allocated(15);
+  std::iota(allocated.begin(), allocated.end(), 0);
+  absl::FixedArray<int, 10> alloced_copy = allocated;
+  EXPECT_THAT(alloced_copy, ElementsAreArray(allocated));
+  EXPECT_FALSE(IsOnStack(alloced_copy));
+}
+
+TEST(FixedArrayTest, MoveCtor) {
+  absl::FixedArray<std::unique_ptr<int>, 10> on_stack(5);
+  for (int i = 0; i < 5; ++i) {
+    on_stack[i] = absl::make_unique<int>(i);
+  }
+
+  absl::FixedArray<std::unique_ptr<int>, 10> stack_copy = std::move(on_stack);
+  for (int i = 0; i < 5; ++i) EXPECT_EQ(*(stack_copy[i]), i);
+  EXPECT_EQ(stack_copy.size(), on_stack.size());
+
+  absl::FixedArray<std::unique_ptr<int>, 10> allocated(15);
+  for (int i = 0; i < 15; ++i) {
+    allocated[i] = absl::make_unique<int>(i);
+  }
+
+  absl::FixedArray<std::unique_ptr<int>, 10> alloced_copy =
+      std::move(allocated);
+  for (int i = 0; i < 15; ++i) EXPECT_EQ(*(alloced_copy[i]), i);
+  EXPECT_EQ(allocated.size(), alloced_copy.size());
+}
+
 TEST(FixedArrayTest, SmallObjects) {
   // Small object arrays
   {
diff --git a/absl/strings/str_cat.h b/absl/strings/str_cat.h
index 5b4c9baacf59..1cf7b11fec71 100644
--- a/absl/strings/str_cat.h
+++ b/absl/strings/str_cat.h
@@ -46,8 +46,7 @@
 // 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, so the equivalent of `StringPrintf("%04x", my_int)` is
-// `absl::StrCat(absl::Hex(my_int, absl::kZeroPad4))`.
+// a `PadSpec` enum.
 //
 // -----------------------------------------------------------------------------
 
diff --git a/absl/strings/substitute.h b/absl/strings/substitute.h
index 76d6d8e966d6..5596a5dbf35a 100644
--- a/absl/strings/substitute.h
+++ b/absl/strings/substitute.h
@@ -45,17 +45,6 @@
 //   SubstituteAndAppend(&s, "My name is $0 and I am $1 years old.", "Bob", 5);
 //   EXPECT_EQ("Hi. My name is Bob and I am 5 years old.", s);
 //
-// Differences from `StringPrintf()`:
-//   * The format std::string does not identify the types of arguments. Instead, the
-//     arguments are implicitly converted to strings. See below for a list of
-//     accepted types.
-//   * Substitutions in the format std::string are identified by a '$' followed by a
-//     single digit. You can use arguments out-of-order and use the same
-//     argument multiple times.
-//   * A '$$' sequence in the format std::string means output a literal '$'
-//     character.
-//   * `Substitute()` is significantly faster than `StringPrintf()`. For very
-//     large strings, it may be orders of magnitude faster.
 //
 // Supported types:
 //   * absl::string_view, std::string, const char* (null is equivalent to "")
@@ -157,8 +146,7 @@ class Arg {
   Arg(bool value)  // NOLINT(runtime/explicit)
       : piece_(value ? "true" : "false") {}
   // `void*` values, with the exception of `char*`, are printed as
-  // `StringPrintf()` with format "%p": e.g. ("0x<hex value>").
-  // However, in the case of `nullptr`, "NULL" is printed.
+  // "0x<hex value>". However, in the case of `nullptr`, "NULL" is printed.
   Arg(const void* value);  // NOLINT(runtime/explicit)
 
   Arg(const Arg&) = delete;