diff --git a/iceoryx_hoofs/test/moduletests/test_vocabulary_expected.cpp b/iceoryx_hoofs/test/moduletests/test_vocabulary_expected.cpp index 51e68d24c51..4ee0bb4e348 100644 --- a/iceoryx_hoofs/test/moduletests/test_vocabulary_expected.cpp +++ b/iceoryx_hoofs/test/moduletests/test_vocabulary_expected.cpp @@ -477,6 +477,22 @@ TEST_F(expected_test, ErrorTypeOnlyMoveAssignmentLeadsToMovedSource) EXPECT_EQ(sutDestination.get_error().m_b, B); } +TEST_F(expected_test, CreateFromInPlaceTypeLeadsToValidErrorOnlySut) +{ + ::testing::Test::RecordProperty("TEST_ID", "91a8ad7f-4843-4bd9-a56b-0561ae6b56cb"); + expected sut{in_place}; + ASSERT_THAT(sut.has_error(), Eq(false)); +} + +TEST_F(expected_test, CreateFromInPlaceTypeLeadsToValidSut) +{ + ::testing::Test::RecordProperty("TEST_ID", "3a527c62-aaea-44ae-9b99-027c19d032b5"); + constexpr int VALUE = 42; + expected sut{in_place, VALUE}; + ASSERT_THAT(sut.has_error(), Eq(false)); + EXPECT_THAT(sut.value(), Eq(VALUE)); +} + TEST_F(expected_test, CreateFromEmptySuccessTypeLeadsToValidSut) { ::testing::Test::RecordProperty("TEST_ID", "0204f08f-fb6d-45bb-aac7-fd14152ab1bf"); diff --git a/iceoryx_hoofs/vocabulary/include/iox/detail/expected.inl b/iceoryx_hoofs/vocabulary/include/iox/detail/expected.inl index c1e1f6562dd..c5e7351d6bb 100644 --- a/iceoryx_hoofs/vocabulary/include/iox/detail/expected.inl +++ b/iceoryx_hoofs/vocabulary/include/iox/detail/expected.inl @@ -101,6 +101,13 @@ inline expected::expected(expected&& { } +template +template +inline expected::expected(in_place_t, Targs&&... args) noexcept + : m_store(in_place_index(), std::forward(args)...) +{ +} + template inline expected& expected::operator=(expected&& rhs) noexcept @@ -264,6 +271,11 @@ inline expected::expected(const success) noexcept { } +template +inline expected::expected(in_place_t) noexcept +{ +} + template inline expected::expected(expected&& rhs) noexcept : m_store(std::move(rhs.m_store)) @@ -292,6 +304,7 @@ inline expected::expected(error&& errorValue) noexcept : m_store(in_place_index(), std::move(errorValue.value)) { } + // AXIVION DISABLE STYLE AutosarC++19_03-A16.0.1: Required for Windows due to MSVC deficiencies #if defined(_WIN32) template diff --git a/iceoryx_hoofs/vocabulary/include/iox/expected.hpp b/iceoryx_hoofs/vocabulary/include/iox/expected.hpp index 2ca2008bea6..1f2a2994708 100644 --- a/iceoryx_hoofs/vocabulary/include/iox/expected.hpp +++ b/iceoryx_hoofs/vocabulary/include/iox/expected.hpp @@ -195,6 +195,11 @@ class IOX_NO_DISCARD expected final : public FunctionalInterface) noexcept; + /// @brief Creates an expected which is signaling success. This mirrors the c'tor for the 'expected' with a + /// 'ValueType'. + /// @param[in] in_place_t compile time variable to distinguish between constructors with certain behavior + explicit expected(in_place_t) noexcept; + /// @brief constructs an expected which is signaling an error and stores the /// error value provided by errorValue /// @param[in] errorValue error value which will be stored in the expected @@ -277,6 +282,13 @@ class IOX_NO_DISCARD expected final /// ValueType or ErrorType to correctly invalidate the stored object expected(expected&& rhs) noexcept; + /// @brief Creates an expected which is signaling success and perfectly forwards + /// the args to the constructor of ValueType + /// @param[in] in_place_t compile time variable to distinguish between constructors with certain behavior + /// @param[in] args... arguments which will be forwarded to the 'ValueType' constructor + template + explicit expected(in_place_t, Targs&&... args) noexcept; + /// @brief calls the destructor of the success value or error value - depending on what /// is stored in the expected ~expected() noexcept = default;