In-place construction for Try
authorYedidya Feldblum <yfeldblum@fb.com>
Sun, 2 Jul 2017 17:22:35 +0000 (10:22 -0700)
committerFacebook Github Bot <facebook-github-bot@users.noreply.github.com>
Sun, 2 Jul 2017 17:40:23 +0000 (10:40 -0700)
Summary:
[Folly] In-place construction for `Try`.

Using `in_place` as the first argumenbt. Avoid move operations.

Reviewed By: Orvid

Differential Revision: D5362568

fbshipit-source-id: 5c2aaf5dba1253c59e384940add411f0f2b570b2

folly/Try.h
folly/test/TryTest.cpp

index f115a34ab333db0961556f3571415cfd36773366..df48794e656258c3dbc4639e65027407b4b1ea42 100644 (file)
@@ -21,6 +21,7 @@
 #include <folly/Memory.h>
 #include <folly/Portability.h>
 #include <folly/Unit.h>
+#include <folly/Utility.h>
 #include <exception>
 #include <stdexcept>
 #include <type_traits>
@@ -81,6 +82,11 @@ class Try {
    */
   explicit Try(T&& v) : contains_(Contains::VALUE), value_(std::move(v)) {}
 
+  template <typename... Args>
+  explicit Try(in_place_t, Args&&... args) noexcept(
+      noexcept(::new (nullptr) T(std::declval<Args&&>()...)))
+      : contains_(Contains::VALUE), value_(std::forward<Args>(args)...) {}
+
   /// Implicit conversion from Try<void> to Try<Unit>
   template <class T2 = T>
   /* implicit */
index 49517bf5b58bd7b7cb5efb032f2fd5acb81c61f3..ae9e301fadc7542de42ddc7d33aba6b6e5a996f2 100644 (file)
 #include <glog/logging.h>
 
 #include <folly/Memory.h>
+#include <folly/Traits.h>
 #include <folly/portability/GTest.h>
 
 using namespace folly;
 
-TEST(Try, basic) {
-  class A {
-   public:
-    A(int x) : x_(x) {}
-
-    int x() const {
-      return x_;
-    }
-   private:
-    int x_;
-  };
+namespace {
 
+class A {
+ public:
+  explicit A(int x) : x_(x) {}
+
+  int x() const {
+    return x_;
+  }
+ private:
+  int x_;
+};
+}
+
+TEST(Try, basic) {
   A a(5);
   Try<A> t_a(std::move(a));
 
@@ -43,6 +47,18 @@ TEST(Try, basic) {
   EXPECT_EQ(5, t_a.value().x());
 }
 
+TEST(Try, in_place) {
+  Try<A> t_a(in_place, 5);
+
+  EXPECT_EQ(5, t_a.value().x());
+}
+
+TEST(Try, in_place_nested) {
+  Try<Try<A>> t_t_a(in_place, in_place, 5);
+
+  EXPECT_EQ(5, t_t_a.value().value().x());
+}
+
 // Make sure we can copy Trys for copyable types
 TEST(Try, copy) {
   Try<int> t;