mirror of
https://github.com/ETLCPP/etl.git
synced 2026-11-09 22:59:47 +08:00
Added result type
This commit is contained in:
parent
6c97ceaa87
commit
81807b2fd2
@ -256,6 +256,18 @@ namespace etl
|
|||||||
using add_cv_t = typename add_cv<T>::type;
|
using add_cv_t = typename add_cv<T>::type;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
//***************************************************************************
|
||||||
|
/// remove_cvref
|
||||||
|
template <typename T> struct remove_cvref
|
||||||
|
{
|
||||||
|
typedef typename remove_cv<typename remove_reference<T>::type>::type type;
|
||||||
|
};
|
||||||
|
|
||||||
|
#if ETL_CPP11_SUPPORTED
|
||||||
|
template <typename T>
|
||||||
|
using remove_cvref_t = typename remove_cvref<T>::type;
|
||||||
|
#endif
|
||||||
|
|
||||||
//***************************************************************************
|
//***************************************************************************
|
||||||
/// is_integral
|
/// is_integral
|
||||||
template <typename T> struct is_integral : false_type {};
|
template <typename T> struct is_integral : false_type {};
|
||||||
@ -590,8 +602,8 @@ namespace etl
|
|||||||
{
|
{
|
||||||
typedef typename etl::remove_reference<T>::type U;
|
typedef typename etl::remove_reference<T>::type U;
|
||||||
typedef typename etl::conditional<etl::is_array<U>::value,
|
typedef typename etl::conditional<etl::is_array<U>::value,
|
||||||
typename etl::remove_extent<U>::type*,
|
typename etl::remove_extent<U>::type*,
|
||||||
typename etl::remove_cv<U>::type>::type type;
|
typename etl::remove_cv<U>::type>::type type;
|
||||||
};
|
};
|
||||||
|
|
||||||
#if ETL_CPP11_SUPPORTED
|
#if ETL_CPP11_SUPPORTED
|
||||||
@ -896,6 +908,19 @@ namespace etl
|
|||||||
using add_cv_t = typename std::add_cv<T>::type;
|
using add_cv_t = typename std::add_cv<T>::type;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
//***************************************************************************
|
||||||
|
/// remove_cvref
|
||||||
|
///\ingroup type_traits
|
||||||
|
template <typename T> struct remove_cvref
|
||||||
|
{
|
||||||
|
typedef typename std::remove_cv<typename std::remove_reference<T>::type>::type type;
|
||||||
|
};
|
||||||
|
|
||||||
|
#if ETL_CPP11_SUPPORTED
|
||||||
|
template <typename T>
|
||||||
|
using remove_cvref_t = typename etl::remove_cvref<T>::type;
|
||||||
|
#endif
|
||||||
|
|
||||||
//***************************************************************************
|
//***************************************************************************
|
||||||
/// is_integral
|
/// is_integral
|
||||||
///\ingroup type_traits
|
///\ingroup type_traits
|
||||||
|
|||||||
@ -44,6 +44,8 @@ SOFTWARE.
|
|||||||
#include "../visitor.h"
|
#include "../visitor.h"
|
||||||
#include "../memory.h"
|
#include "../memory.h"
|
||||||
|
|
||||||
|
#include <type_traits>
|
||||||
|
|
||||||
#if defined(ETL_COMPILER_KEIL)
|
#if defined(ETL_COMPILER_KEIL)
|
||||||
#pragma diag_suppress 940
|
#pragma diag_suppress 940
|
||||||
#pragma diag_suppress 111
|
#pragma diag_suppress 111
|
||||||
@ -87,7 +89,7 @@ namespace etl
|
|||||||
{
|
{
|
||||||
private:
|
private:
|
||||||
|
|
||||||
using type = etl::remove_reference_t<T>;
|
using type = etl::remove_cvref_t<T>;
|
||||||
|
|
||||||
//***********************************
|
//***********************************
|
||||||
template <typename Type, typename T1, typename... TRest>
|
template <typename Type, typename T1, typename... TRest>
|
||||||
@ -528,15 +530,15 @@ namespace etl
|
|||||||
//***************************************************************************
|
//***************************************************************************
|
||||||
/// Constructor from a value.
|
/// Constructor from a value.
|
||||||
//***************************************************************************
|
//***************************************************************************
|
||||||
template <typename T, etl::enable_if_t<!etl::is_same<etl::remove_reference_t<T>, variant>::value, int> = 0>
|
template <typename T, etl::enable_if_t<!etl::is_same<etl::remove_cvref_t<T>, variant>::value, int> = 0>
|
||||||
ETL_CONSTEXPR14 variant(T&& value)
|
ETL_CONSTEXPR14 variant(T&& value)
|
||||||
: data()
|
: data()
|
||||||
, operation(operation_type<etl::remove_reference_t<T>, etl::is_copy_constructible<etl::remove_reference_t<T>>::value, etl::is_move_constructible<etl::remove_reference_t<T>>::value>::do_operation)
|
, operation(operation_type<etl::remove_cvref_t<T>, etl::is_copy_constructible<etl::remove_cvref_t<T>>::value, etl::is_move_constructible<etl::remove_cvref_t<T>>::value>::do_operation)
|
||||||
, type_id(etl::private_variant::parameter_pack<TTypes...>::template index_of_type<etl::remove_reference_t<T>>::value)
|
, type_id(etl::private_variant::parameter_pack<TTypes...>::template index_of_type<etl::remove_cvref_t<T>>::value)
|
||||||
{
|
{
|
||||||
static_assert(etl::is_one_of<etl::remove_reference_t<T>, TTypes...>::value, "Unsupported type");
|
static_assert(etl::is_one_of<etl::remove_cvref_t<T>, TTypes...>::value, "Unsupported type");
|
||||||
|
|
||||||
construct_in_place<etl::remove_reference_t<T>>(data, etl::forward<T>(value));
|
construct_in_place<etl::remove_cvref_t<T>>(data, etl::forward<T>(value));
|
||||||
}
|
}
|
||||||
|
|
||||||
//***************************************************************************
|
//***************************************************************************
|
||||||
@ -545,12 +547,12 @@ namespace etl
|
|||||||
template <typename T, typename... TArgs>
|
template <typename T, typename... TArgs>
|
||||||
ETL_CONSTEXPR14 explicit variant(etl::in_place_type_t<T>, TArgs&&... args)
|
ETL_CONSTEXPR14 explicit variant(etl::in_place_type_t<T>, TArgs&&... args)
|
||||||
: data()
|
: data()
|
||||||
, operation(operation_type<etl::remove_reference_t<T>, etl::is_copy_constructible<etl::remove_reference_t<T>>::value, etl::is_move_constructible<etl::remove_reference_t<T>>::value>::do_operation)
|
, operation(operation_type<etl::remove_cvref_t<T>, etl::is_copy_constructible<etl::remove_cvref_t<T>>::value, etl::is_move_constructible<etl::remove_cvref_t<T>>::value>::do_operation)
|
||||||
, type_id(etl::private_variant::parameter_pack<TTypes...>::template index_of_type<etl::remove_reference_t<T>>::value)
|
, type_id(etl::private_variant::parameter_pack<TTypes...>::template index_of_type<etl::remove_cvref_t<T>>::value)
|
||||||
{
|
{
|
||||||
static_assert(etl::is_one_of<etl::remove_reference_t<T>, TTypes...>::value, "Unsupported type");
|
static_assert(etl::is_one_of<etl::remove_cvref_t<T>, TTypes...>::value, "Unsupported type");
|
||||||
|
|
||||||
construct_in_place_args<etl::remove_reference_t<T>>(data, etl::forward<TArgs>(args)...);
|
construct_in_place_args<etl::remove_cvref_t<T>>(data, etl::forward<TArgs>(args)...);
|
||||||
}
|
}
|
||||||
|
|
||||||
//***************************************************************************
|
//***************************************************************************
|
||||||
@ -576,12 +578,12 @@ namespace etl
|
|||||||
template <typename T, typename U, typename... TArgs >
|
template <typename T, typename U, typename... TArgs >
|
||||||
ETL_CONSTEXPR14 explicit variant(etl::in_place_type_t<T>, std::initializer_list<U> init, TArgs&&... args)
|
ETL_CONSTEXPR14 explicit variant(etl::in_place_type_t<T>, std::initializer_list<U> init, TArgs&&... args)
|
||||||
: data()
|
: data()
|
||||||
, operation(operation_type<etl::remove_reference_t<T>, etl::is_copy_constructible<etl::remove_reference_t<T>>::value, etl::is_move_constructible<etl::remove_reference_t<T>>::value>::do_operation)
|
, operation(operation_type<etl::remove_cvref_t<T>, etl::is_copy_constructible<etl::remove_cvref_t<T>>::value, etl::is_move_constructible<etl::remove_cvref_t<T>>::value>::do_operation)
|
||||||
, type_id(private_variant::parameter_pack<TTypes...>:: template index_of_type<etl::remove_reference_t<T>>::value)
|
, type_id(private_variant::parameter_pack<TTypes...>:: template index_of_type<etl::remove_cvref_t<T>>::value)
|
||||||
{
|
{
|
||||||
static_assert(etl::is_one_of<etl::remove_reference_t<T>, TTypes...> ::value, "Unsupported type");
|
static_assert(etl::is_one_of<etl::remove_cvref_t<T>, TTypes...> ::value, "Unsupported type");
|
||||||
|
|
||||||
construct_in_place_args<etl::remove_reference_t<T>>(data, init, etl::forward<TArgs>(args)...);
|
construct_in_place_args<etl::remove_cvref_t<T>>(data, init, etl::forward<TArgs>(args)...);
|
||||||
}
|
}
|
||||||
|
|
||||||
//***************************************************************************
|
//***************************************************************************
|
||||||
@ -671,7 +673,7 @@ namespace etl
|
|||||||
{
|
{
|
||||||
static_assert(etl::is_one_of<T, TTypes...>::value, "Unsupported type");
|
static_assert(etl::is_one_of<T, TTypes...>::value, "Unsupported type");
|
||||||
|
|
||||||
using type = etl::remove_reference_t<T>;
|
using type = etl::remove_cvref_t<T>;
|
||||||
|
|
||||||
operation(private_variant::Destroy, data, nullptr);
|
operation(private_variant::Destroy, data, nullptr);
|
||||||
|
|
||||||
@ -688,10 +690,10 @@ namespace etl
|
|||||||
/// Move assignment operator for type.
|
/// Move assignment operator for type.
|
||||||
///\param value The value to assign.
|
///\param value The value to assign.
|
||||||
//***************************************************************************
|
//***************************************************************************
|
||||||
template <typename T, etl::enable_if_t<!etl::is_same<etl::remove_reference_t<T>, variant>::value, int> = 0>
|
template <typename T, etl::enable_if_t<!etl::is_same<etl::remove_cvref_t<T>, variant>::value, int> = 0>
|
||||||
variant& operator =(T&& value)
|
variant& operator =(T&& value)
|
||||||
{
|
{
|
||||||
using type = etl::remove_reference_t<T>;
|
using type = etl::remove_cvref_t<T>;
|
||||||
|
|
||||||
static_assert(etl::is_one_of<type, TTypes...>::value, "Unsupported type");
|
static_assert(etl::is_one_of<type, TTypes...>::value, "Unsupported type");
|
||||||
|
|
||||||
@ -820,7 +822,7 @@ namespace etl
|
|||||||
template <typename T>
|
template <typename T>
|
||||||
static void construct_in_place(char* pstorage, const T& value)
|
static void construct_in_place(char* pstorage, const T& value)
|
||||||
{
|
{
|
||||||
using type = etl::remove_reference_t<T>;
|
using type = etl::remove_cvref_t<T>;
|
||||||
|
|
||||||
::new (pstorage) type(value);
|
::new (pstorage) type(value);
|
||||||
}
|
}
|
||||||
@ -831,7 +833,7 @@ namespace etl
|
|||||||
template <typename T>
|
template <typename T>
|
||||||
static void construct_in_place(char* pstorage, T&& value)
|
static void construct_in_place(char* pstorage, T&& value)
|
||||||
{
|
{
|
||||||
using type = etl::remove_reference_t<T>;
|
using type = etl::remove_cvref_t<T>;
|
||||||
|
|
||||||
::new (pstorage) type(etl::move(value));
|
::new (pstorage) type(etl::move(value));
|
||||||
}
|
}
|
||||||
@ -842,7 +844,7 @@ namespace etl
|
|||||||
template <typename T, typename... TArgs>
|
template <typename T, typename... TArgs>
|
||||||
static void construct_in_place_args(char* pstorage, TArgs&&... args)
|
static void construct_in_place_args(char* pstorage, TArgs&&... args)
|
||||||
{
|
{
|
||||||
using type = etl::remove_reference_t<T>;
|
using type = etl::remove_cvref_t<T>;
|
||||||
|
|
||||||
::new (pstorage) type(etl::forward<TArgs>(args)...);
|
::new (pstorage) type(etl::forward<TArgs>(args)...);
|
||||||
}
|
}
|
||||||
@ -853,7 +855,7 @@ namespace etl
|
|||||||
template <typename T>
|
template <typename T>
|
||||||
static void default_construct_in_place(char* pstorage)
|
static void default_construct_in_place(char* pstorage)
|
||||||
{
|
{
|
||||||
using type = etl::remove_reference_t<T>;
|
using type = etl::remove_cvref_t<T>;
|
||||||
|
|
||||||
::new (pstorage) type();
|
::new (pstorage) type();
|
||||||
}
|
}
|
||||||
|
|||||||
326
include/etl/result.h
Normal file
326
include/etl/result.h
Normal file
@ -0,0 +1,326 @@
|
|||||||
|
///\file
|
||||||
|
|
||||||
|
/******************************************************************************
|
||||||
|
The MIT License(MIT)
|
||||||
|
|
||||||
|
Embedded Template Library.
|
||||||
|
https://github.com/ETLCPP/etl
|
||||||
|
https://www.etlcpp.com
|
||||||
|
|
||||||
|
Copyright(c) 2021 jwellbelove
|
||||||
|
|
||||||
|
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
of this software and associated documentation files(the "Software"), to deal
|
||||||
|
in the Software without restriction, including without limitation the rights
|
||||||
|
to use, copy, modify, merge, publish, distribute, sublicense, and / or sell
|
||||||
|
copies of the Software, and to permit persons to whom the Software is
|
||||||
|
furnished to do so, subject to the following conditions :
|
||||||
|
|
||||||
|
The above copyright notice and this permission notice shall be included in all
|
||||||
|
copies or substantial portions of the Software.
|
||||||
|
|
||||||
|
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE
|
||||||
|
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||||
|
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||||
|
SOFTWARE.
|
||||||
|
******************************************************************************/
|
||||||
|
|
||||||
|
#ifndef ETL_RESULT_INCLUDED
|
||||||
|
#define ETL_RESULT_INCLUDED
|
||||||
|
|
||||||
|
///\defgroup result result
|
||||||
|
///\ingroup utilities
|
||||||
|
|
||||||
|
#include "platform.h"
|
||||||
|
#include "optional.h"
|
||||||
|
#include "variant.h"
|
||||||
|
|
||||||
|
#if ETL_CPP11_NOT_SUPPORTED
|
||||||
|
#if !defined(ETL_IN_UNIT_TEST)
|
||||||
|
#error NOT SUPPORTED FOR C++03 OR BELOW
|
||||||
|
#endif
|
||||||
|
#else
|
||||||
|
|
||||||
|
namespace etl
|
||||||
|
{
|
||||||
|
//*****************************************************************************
|
||||||
|
/// Result type.
|
||||||
|
//*****************************************************************************
|
||||||
|
template <typename TValue, typename TError>
|
||||||
|
class result
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
/// Cannot be default constructed
|
||||||
|
//*******************************************
|
||||||
|
result() = delete;
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
/// Copy constructor
|
||||||
|
//*******************************************
|
||||||
|
result(const result& other)
|
||||||
|
: data(other.data)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
/// Move constructor
|
||||||
|
//*******************************************
|
||||||
|
result(result&& other)
|
||||||
|
: data(etl::move(other.data))
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
// Construct from a value
|
||||||
|
//*******************************************
|
||||||
|
result(const TValue& value)
|
||||||
|
: data(value)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
// Move construct from a value
|
||||||
|
//*******************************************
|
||||||
|
result(TValue&& value)
|
||||||
|
: data(etl::move(value))
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
/// Construct from error
|
||||||
|
//*******************************************
|
||||||
|
result(const TError& err)
|
||||||
|
: data(err)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
/// Move construct from error
|
||||||
|
//*******************************************
|
||||||
|
result(TError&& err)
|
||||||
|
: data(etl::move(err))
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
/// Copy assign
|
||||||
|
//*******************************************
|
||||||
|
result& operator =(const result& other)
|
||||||
|
{
|
||||||
|
data = other.data;
|
||||||
|
return *this;
|
||||||
|
}
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
/// Move assign
|
||||||
|
//*******************************************
|
||||||
|
result& operator =(result&& other)
|
||||||
|
{
|
||||||
|
data = etl::move(other.data);
|
||||||
|
return *this;
|
||||||
|
}
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
/// Copy assign from value
|
||||||
|
//*******************************************
|
||||||
|
result& operator =(const TValue& value)
|
||||||
|
{
|
||||||
|
data = value;
|
||||||
|
return *this;
|
||||||
|
}
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
/// Move assign from value
|
||||||
|
//*******************************************
|
||||||
|
result& operator =(TValue&& value)
|
||||||
|
{
|
||||||
|
data = etl::move(value);
|
||||||
|
return *this;
|
||||||
|
}
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
/// Copy assign from error
|
||||||
|
//*******************************************
|
||||||
|
result& operator =(const TError& err)
|
||||||
|
{
|
||||||
|
data = err;
|
||||||
|
return *this;
|
||||||
|
}
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
/// Move assign from error
|
||||||
|
//*******************************************
|
||||||
|
result& operator =(TError&& err)
|
||||||
|
{
|
||||||
|
data = etl::move(err);
|
||||||
|
return *this;
|
||||||
|
}
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
/// <b>true</b> if result contains a value
|
||||||
|
//*******************************************
|
||||||
|
bool is_value() const
|
||||||
|
{
|
||||||
|
return (data.index() == 0U);
|
||||||
|
}
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
/// <b>true</b> if result contains an error
|
||||||
|
//*******************************************
|
||||||
|
bool is_error() const
|
||||||
|
{
|
||||||
|
return (data.index() == 1U);
|
||||||
|
}
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
/// Returns a const reference to the value.
|
||||||
|
/// Undefined if the result does not contain an value.
|
||||||
|
//*******************************************
|
||||||
|
const TValue& value() const
|
||||||
|
{
|
||||||
|
return etl::get<TValue>(data);
|
||||||
|
}
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
/// Returns an rvalue reference to the value.
|
||||||
|
/// Undefined if the result does not contain an value.
|
||||||
|
//*******************************************
|
||||||
|
TValue&& value()
|
||||||
|
{
|
||||||
|
return etl::get<TValue>(etl::move(data));
|
||||||
|
}
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
/// Returns a const reference to the error.
|
||||||
|
/// Undefined if the result does not contain an error.
|
||||||
|
//*******************************************
|
||||||
|
const TError& error() const
|
||||||
|
{
|
||||||
|
return etl::get<TError>(data);
|
||||||
|
}
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
/// Returns an rvalue reference to the error.
|
||||||
|
/// Undefined if the result does not contain an error.
|
||||||
|
//*******************************************
|
||||||
|
TError&& error()
|
||||||
|
{
|
||||||
|
return etl::get<TError>(etl::move(data));
|
||||||
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
|
||||||
|
etl::variant<TValue, TError> data;
|
||||||
|
};
|
||||||
|
|
||||||
|
//*****************************************************************************
|
||||||
|
/// Result type.
|
||||||
|
/// Specialisation for void value type.
|
||||||
|
//*****************************************************************************
|
||||||
|
template<typename TError>
|
||||||
|
class result<void, TError>
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
/// Cannot be default constructed
|
||||||
|
//*******************************************
|
||||||
|
result() = delete;
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
/// Copy constructor
|
||||||
|
//*******************************************
|
||||||
|
result(const result& other)
|
||||||
|
: data(other.data)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
/// Move constructor
|
||||||
|
//*******************************************
|
||||||
|
result(result&& other)
|
||||||
|
: data(etl::move(other.data))
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
/// Construct from error
|
||||||
|
//*******************************************
|
||||||
|
result(const TError& err)
|
||||||
|
: data(err)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
/// Move construct from error
|
||||||
|
//*******************************************
|
||||||
|
result(TError&& err)
|
||||||
|
: data(etl::move(err))
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
/// Copy assign from error
|
||||||
|
//*******************************************
|
||||||
|
result& operator =(const TError& err)
|
||||||
|
{
|
||||||
|
data = err;
|
||||||
|
return *this;
|
||||||
|
}
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
/// Move assign from error
|
||||||
|
//*******************************************
|
||||||
|
result& operator =(TError&& err)
|
||||||
|
{
|
||||||
|
data = etl::move(err);
|
||||||
|
return *this;
|
||||||
|
}
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
/// <b>true</b> if result contains a value
|
||||||
|
//*******************************************
|
||||||
|
bool is_value() const
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
/// <b>true</b> if result contains an error
|
||||||
|
//*******************************************
|
||||||
|
bool is_error() const
|
||||||
|
{
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
/// Returns a const reference to the error.
|
||||||
|
/// Undefined if the result does not contain an error.
|
||||||
|
//*******************************************
|
||||||
|
const TError& error() const
|
||||||
|
{
|
||||||
|
return etl::get<TError>(data);
|
||||||
|
}
|
||||||
|
|
||||||
|
//*******************************************
|
||||||
|
/// Returns an rvalue reference to the error.
|
||||||
|
/// Undefined if the result does not contain an error.
|
||||||
|
//*******************************************
|
||||||
|
TError&& error()
|
||||||
|
{
|
||||||
|
return etl::get<TError>(etl::move(data));
|
||||||
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
|
||||||
|
etl::variant<etl::monostate, TError> data;
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
@ -244,6 +244,18 @@ namespace etl
|
|||||||
using add_cv_t = typename add_cv<T>::type;
|
using add_cv_t = typename add_cv<T>::type;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
//***************************************************************************
|
||||||
|
/// remove_cvref
|
||||||
|
template <typename T> struct remove_cvref
|
||||||
|
{
|
||||||
|
typedef typename remove_cv<typename remove_reference<T>::type>::type type;
|
||||||
|
};
|
||||||
|
|
||||||
|
#if ETL_CPP11_SUPPORTED
|
||||||
|
template <typename T>
|
||||||
|
using remove_cvref_t = typename remove_cvref<T>::type;
|
||||||
|
#endif
|
||||||
|
|
||||||
//***************************************************************************
|
//***************************************************************************
|
||||||
/// is_integral
|
/// is_integral
|
||||||
template <typename T> struct is_integral : false_type {};
|
template <typename T> struct is_integral : false_type {};
|
||||||
@ -578,8 +590,8 @@ namespace etl
|
|||||||
{
|
{
|
||||||
typedef typename etl::remove_reference<T>::type U;
|
typedef typename etl::remove_reference<T>::type U;
|
||||||
typedef typename etl::conditional<etl::is_array<U>::value,
|
typedef typename etl::conditional<etl::is_array<U>::value,
|
||||||
typename etl::remove_extent<U>::type*,
|
typename etl::remove_extent<U>::type*,
|
||||||
typename etl::remove_cv<U>::type>::type type;
|
typename etl::remove_cv<U>::type>::type type;
|
||||||
};
|
};
|
||||||
|
|
||||||
#if ETL_CPP11_SUPPORTED
|
#if ETL_CPP11_SUPPORTED
|
||||||
@ -884,6 +896,19 @@ namespace etl
|
|||||||
using add_cv_t = typename std::add_cv<T>::type;
|
using add_cv_t = typename std::add_cv<T>::type;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
//***************************************************************************
|
||||||
|
/// remove_cvref
|
||||||
|
///\ingroup type_traits
|
||||||
|
template <typename T> struct remove_cvref
|
||||||
|
{
|
||||||
|
typedef typename std::remove_cv<typename std::remove_reference<T>::type>::type type;
|
||||||
|
};
|
||||||
|
|
||||||
|
#if ETL_CPP11_SUPPORTED
|
||||||
|
template <typename T>
|
||||||
|
using remove_cvref_t = typename etl::remove_cvref<T>::type;
|
||||||
|
#endif
|
||||||
|
|
||||||
//***************************************************************************
|
//***************************************************************************
|
||||||
/// is_integral
|
/// is_integral
|
||||||
///\ingroup type_traits
|
///\ingroup type_traits
|
||||||
|
|||||||
341
test/test_result.cpp
Normal file
341
test/test_result.cpp
Normal file
@ -0,0 +1,341 @@
|
|||||||
|
/******************************************************************************
|
||||||
|
The MIT License(MIT)
|
||||||
|
|
||||||
|
Embedded Template Library.
|
||||||
|
https://github.com/ETLCPP/etl
|
||||||
|
https://www.etlcpp.com
|
||||||
|
|
||||||
|
Copyright(c) 2017 jwellbelove
|
||||||
|
|
||||||
|
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
of this software and associated documentation files(the "Software"), to deal
|
||||||
|
in the Software without restriction, including without limitation the rights
|
||||||
|
to use, copy, modify, merge, publish, distribute, sublicense, and / or sell
|
||||||
|
copies of the Software, and to permit persons to whom the Software is
|
||||||
|
furnished to do so, subject to the following conditions :
|
||||||
|
|
||||||
|
The above copyright notice and this permission notice shall be included in all
|
||||||
|
copies or substantial portions of the Software.
|
||||||
|
|
||||||
|
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE
|
||||||
|
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||||
|
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||||
|
SOFTWARE.
|
||||||
|
******************************************************************************/
|
||||||
|
|
||||||
|
#include "unit_test_framework.h"
|
||||||
|
|
||||||
|
#include "etl/result.h"
|
||||||
|
|
||||||
|
#include <string>
|
||||||
|
|
||||||
|
namespace
|
||||||
|
{
|
||||||
|
SUITE(test_result)
|
||||||
|
{
|
||||||
|
struct Value
|
||||||
|
{
|
||||||
|
std::string v;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct ValueM
|
||||||
|
{
|
||||||
|
ValueM()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
ValueM(const std::string& v_) : v(v_)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
ValueM(ValueM&& other)
|
||||||
|
: v(etl::move(other.v))
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
ValueM& operator =(ValueM&& rhs)
|
||||||
|
{
|
||||||
|
v = etl::move(rhs.v);
|
||||||
|
return *this;
|
||||||
|
}
|
||||||
|
|
||||||
|
//ValueM(const ValueM&) = delete;
|
||||||
|
//ValueM& operator =(const ValueM&) = delete;
|
||||||
|
|
||||||
|
ValueM(const ValueM& other)
|
||||||
|
: v(other.v)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
ValueM& operator =(const ValueM& rhs)
|
||||||
|
{
|
||||||
|
v = rhs.v;
|
||||||
|
return *this;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::string v;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct Error
|
||||||
|
{
|
||||||
|
std::string e;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct ErrorM
|
||||||
|
{
|
||||||
|
ErrorM()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
ErrorM(const std::string& e_)
|
||||||
|
: e(e_)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
ErrorM(ErrorM&& other)
|
||||||
|
: e(etl::move(other.e))
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
ErrorM& operator =(ErrorM&& rhs)
|
||||||
|
{
|
||||||
|
e = etl::move(rhs.e);
|
||||||
|
return *this;
|
||||||
|
}
|
||||||
|
|
||||||
|
ErrorM(const ErrorM& other)
|
||||||
|
: e(other.e)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
ErrorM& operator =(const ErrorM& rhs)
|
||||||
|
{
|
||||||
|
e = rhs.e;
|
||||||
|
return *this;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::string e;
|
||||||
|
};
|
||||||
|
|
||||||
|
using Result = etl::result<Value, Error>;
|
||||||
|
using ResultV = etl::result<void, Error>;
|
||||||
|
using ResultM = etl::result<ValueM, ErrorM>;
|
||||||
|
|
||||||
|
//*************************************************************************
|
||||||
|
TEST(test_constructor_for_result_with_value)
|
||||||
|
{
|
||||||
|
Value input = { "value 1" };
|
||||||
|
Result result(input);
|
||||||
|
|
||||||
|
Value output = result.value();
|
||||||
|
|
||||||
|
CHECK(result.is_value());
|
||||||
|
CHECK(!result.is_error());
|
||||||
|
CHECK(output.v == input.v);
|
||||||
|
}
|
||||||
|
|
||||||
|
//*************************************************************************
|
||||||
|
TEST(test_constructor_for_const_result_with_value)
|
||||||
|
{
|
||||||
|
Value input = { "value 1" };
|
||||||
|
const Result result(input);
|
||||||
|
|
||||||
|
const Value& output = result.value();
|
||||||
|
|
||||||
|
CHECK(result.is_value());
|
||||||
|
CHECK(!result.is_error());
|
||||||
|
CHECK(output.v == input.v);
|
||||||
|
}
|
||||||
|
|
||||||
|
//*************************************************************************
|
||||||
|
TEST(test_constructor_for_moveable_result_with_value)
|
||||||
|
{
|
||||||
|
ValueM input = { "value 1" };
|
||||||
|
ResultM result(etl::move(input));
|
||||||
|
|
||||||
|
ValueM output = etl::move(result.value());
|
||||||
|
|
||||||
|
CHECK(result.is_value());
|
||||||
|
CHECK(!result.is_error());
|
||||||
|
CHECK(output.v == std::string("value 1"));
|
||||||
|
}
|
||||||
|
|
||||||
|
//*************************************************************************
|
||||||
|
TEST(test_constructor_for_moveable_const_result_with_value)
|
||||||
|
{
|
||||||
|
ValueM input = { "value 1" };
|
||||||
|
const ResultM result(etl::move(input));
|
||||||
|
|
||||||
|
ValueM output = etl::move(result.value());
|
||||||
|
|
||||||
|
CHECK(result.is_value());
|
||||||
|
CHECK(!result.is_error());
|
||||||
|
CHECK(output.v == std::string("value 1"));
|
||||||
|
}
|
||||||
|
|
||||||
|
//*************************************************************************
|
||||||
|
TEST(test_constructor_for_result_with_error)
|
||||||
|
{
|
||||||
|
Error input = { "error 1" };
|
||||||
|
Result result(input);
|
||||||
|
|
||||||
|
Error output = result.error();
|
||||||
|
|
||||||
|
CHECK(!result.is_value());
|
||||||
|
CHECK(result.is_error());
|
||||||
|
CHECK(output.e == input.e);
|
||||||
|
}
|
||||||
|
|
||||||
|
//*************************************************************************
|
||||||
|
TEST(test_constructor_for_const_result_with_error)
|
||||||
|
{
|
||||||
|
Error input = { "error 1" };
|
||||||
|
const Result result(input);
|
||||||
|
|
||||||
|
const Error& output = result.error();
|
||||||
|
|
||||||
|
CHECK(!result.is_value());
|
||||||
|
CHECK(result.is_error());
|
||||||
|
CHECK(output.e == input.e);
|
||||||
|
}
|
||||||
|
|
||||||
|
//*************************************************************************
|
||||||
|
TEST(test_constructor_for_moveable_result_with_error)
|
||||||
|
{
|
||||||
|
ErrorM input = { "error 1" };
|
||||||
|
ResultM result(etl::move(input));
|
||||||
|
|
||||||
|
ErrorM output = etl::move(result.error());
|
||||||
|
|
||||||
|
CHECK(!result.is_value());
|
||||||
|
CHECK(result.is_error());
|
||||||
|
CHECK(output.e == std::string("error 1"));
|
||||||
|
}
|
||||||
|
|
||||||
|
//*************************************************************************
|
||||||
|
TEST(test_constructor_for_moveable_const_result_with_error)
|
||||||
|
{
|
||||||
|
ErrorM input = { "error 1" };
|
||||||
|
const ResultM result(etl::move(input));
|
||||||
|
|
||||||
|
ErrorM output = etl::move(result.error());
|
||||||
|
|
||||||
|
CHECK(!result.is_value());
|
||||||
|
CHECK(result.is_error());
|
||||||
|
CHECK(output.e == std::string("error 1"));
|
||||||
|
}
|
||||||
|
|
||||||
|
//*************************************************************************
|
||||||
|
TEST(test_constructor_for_result_void_value_with_error)
|
||||||
|
{
|
||||||
|
Error input = { "error 1" };
|
||||||
|
ResultV result(input);
|
||||||
|
|
||||||
|
Error output = result.error();
|
||||||
|
|
||||||
|
CHECK(!result.is_value());
|
||||||
|
CHECK(result.is_error());
|
||||||
|
CHECK(output.e == input.e);
|
||||||
|
}
|
||||||
|
|
||||||
|
//*************************************************************************
|
||||||
|
TEST(test_constructor_for_const_result_void_value_with_error)
|
||||||
|
{
|
||||||
|
Error input = { "error 1" };
|
||||||
|
const ResultV result(input);
|
||||||
|
|
||||||
|
const Error& output = result.error();
|
||||||
|
|
||||||
|
CHECK(!result.is_value());
|
||||||
|
CHECK(result.is_error());
|
||||||
|
CHECK(output.e == input.e);
|
||||||
|
}
|
||||||
|
|
||||||
|
//*************************************************************************
|
||||||
|
TEST(test_constructor_for_moveable_result_void_value_with_error)
|
||||||
|
{
|
||||||
|
Error input = { "error 1" };
|
||||||
|
ResultV result(etl::move(input));
|
||||||
|
|
||||||
|
Error output = etl::move(result.error());
|
||||||
|
|
||||||
|
CHECK(!result.is_value());
|
||||||
|
CHECK(result.is_error());
|
||||||
|
CHECK(output.e == std::string("error 1"));
|
||||||
|
}
|
||||||
|
|
||||||
|
//*************************************************************************
|
||||||
|
TEST(test_constructor_for_moveable_const_result_void_value_with_error)
|
||||||
|
{
|
||||||
|
Error input = { "error 1" };
|
||||||
|
const ResultV result(etl::move(input));
|
||||||
|
|
||||||
|
Error output = etl::move(result.error());
|
||||||
|
|
||||||
|
CHECK(!result.is_value());
|
||||||
|
CHECK(result.is_error());
|
||||||
|
CHECK(output.e == std::string("error 1"));
|
||||||
|
}
|
||||||
|
|
||||||
|
//*************************************************************************
|
||||||
|
TEST(test_copy_construct_result)
|
||||||
|
{
|
||||||
|
Value input = { "value 1" };
|
||||||
|
Result result(input);
|
||||||
|
|
||||||
|
Result result2(result);
|
||||||
|
|
||||||
|
Value output = result2.value();
|
||||||
|
|
||||||
|
CHECK(result.is_value());
|
||||||
|
CHECK(!result.is_error());
|
||||||
|
CHECK(result2.is_value());
|
||||||
|
CHECK(!result2.is_error());
|
||||||
|
CHECK(output.v == input.v);
|
||||||
|
}
|
||||||
|
|
||||||
|
//*************************************************************************
|
||||||
|
TEST(test_move_construct_result)
|
||||||
|
{
|
||||||
|
Value input = { "value 1" };
|
||||||
|
Result result(input);
|
||||||
|
|
||||||
|
Result result2(etl::move(result));
|
||||||
|
|
||||||
|
Value output = result.value();
|
||||||
|
Value output2 = result2.value();
|
||||||
|
|
||||||
|
CHECK(result.is_value());
|
||||||
|
CHECK(!result.is_error());
|
||||||
|
CHECK(result2.is_value());
|
||||||
|
CHECK(!result2.is_error());
|
||||||
|
CHECK(output.v != input.v);
|
||||||
|
CHECK(output2.v == input.v);
|
||||||
|
}
|
||||||
|
|
||||||
|
//*************************************************************************
|
||||||
|
TEST(test_move_assign_result)
|
||||||
|
{
|
||||||
|
Value input = { "value 1" };
|
||||||
|
Result result(input);
|
||||||
|
|
||||||
|
Value input2 = { "value 2" };
|
||||||
|
Result result2(result);
|
||||||
|
|
||||||
|
result2 = etl::move(result);
|
||||||
|
|
||||||
|
Value output = result.value();
|
||||||
|
Value output2 = result2.value();
|
||||||
|
|
||||||
|
CHECK(result.is_value());
|
||||||
|
CHECK(!result.is_error());
|
||||||
|
CHECK(result2.is_value());
|
||||||
|
CHECK(!result2.is_error());
|
||||||
|
CHECK(output.v != input.v);
|
||||||
|
CHECK(output2.v == input.v);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
@ -1852,6 +1852,7 @@
|
|||||||
<ClInclude Include="..\..\include\etl\reference_counted_object.h" />
|
<ClInclude Include="..\..\include\etl\reference_counted_object.h" />
|
||||||
<ClInclude Include="..\..\include\etl\message_router_registry.h" />
|
<ClInclude Include="..\..\include\etl\message_router_registry.h" />
|
||||||
<ClInclude Include="..\..\include\etl\rescale.h" />
|
<ClInclude Include="..\..\include\etl\rescale.h" />
|
||||||
|
<ClInclude Include="..\..\include\etl\result.h" />
|
||||||
<ClInclude Include="..\..\include\etl\rms.h" />
|
<ClInclude Include="..\..\include\etl\rms.h" />
|
||||||
<ClInclude Include="..\..\include\etl\scaled_rounding.h" />
|
<ClInclude Include="..\..\include\etl\scaled_rounding.h" />
|
||||||
<ClInclude Include="..\..\include\etl\shared_message.h" />
|
<ClInclude Include="..\..\include\etl\shared_message.h" />
|
||||||
@ -8277,6 +8278,7 @@
|
|||||||
<ClCompile Include="..\test_queue_lockable.cpp" />
|
<ClCompile Include="..\test_queue_lockable.cpp" />
|
||||||
<ClCompile Include="..\test_queue_lockable_small.cpp" />
|
<ClCompile Include="..\test_queue_lockable_small.cpp" />
|
||||||
<ClCompile Include="..\test_rescale.cpp" />
|
<ClCompile Include="..\test_rescale.cpp" />
|
||||||
|
<ClCompile Include="..\test_result.cpp" />
|
||||||
<ClCompile Include="..\test_rms.cpp" />
|
<ClCompile Include="..\test_rms.cpp" />
|
||||||
<ClCompile Include="..\test_shared_message.cpp" />
|
<ClCompile Include="..\test_shared_message.cpp" />
|
||||||
<ClCompile Include="..\test_priority_queue.cpp" />
|
<ClCompile Include="..\test_priority_queue.cpp" />
|
||||||
|
|||||||
@ -1143,6 +1143,9 @@
|
|||||||
<ClInclude Include="..\..\include\etl\byte_stream.h">
|
<ClInclude Include="..\..\include\etl\byte_stream.h">
|
||||||
<Filter>ETL\Utilities</Filter>
|
<Filter>ETL\Utilities</Filter>
|
||||||
</ClInclude>
|
</ClInclude>
|
||||||
|
<ClInclude Include="..\..\include\etl\result.h">
|
||||||
|
<Filter>ETL\Utilities</Filter>
|
||||||
|
</ClInclude>
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<ClCompile Include="..\main.cpp">
|
<ClCompile Include="..\main.cpp">
|
||||||
@ -3005,6 +3008,9 @@
|
|||||||
<ClCompile Include="..\sanity-check\byte_stream.h.t.cpp">
|
<ClCompile Include="..\sanity-check\byte_stream.h.t.cpp">
|
||||||
<Filter>Source Files\Sanity Checks</Filter>
|
<Filter>Source Files\Sanity Checks</Filter>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
|
<ClCompile Include="..\test_result.cpp">
|
||||||
|
<Filter>Source Files</Filter>
|
||||||
|
</ClCompile>
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<None Include="..\..\library.properties">
|
<None Include="..\..\library.properties">
|
||||||
@ -3149,4 +3155,4 @@
|
|||||||
<Filter>Resource Files</Filter>
|
<Filter>Resource Files</Filter>
|
||||||
</Natvis>
|
</Natvis>
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
</Project>
|
</Project>
|
||||||
Loading…
x
Reference in New Issue
Block a user