我开始根据提案实现了
我实现的方式是,绑定有两个重载(使用
这导致返回的expected的进一步连续失去了导致默认构造的错误的上下文。
也许我应该处理被称为
以下是我最初的实施方式:
在这里,如果没有值存在于包装的重载中,我们会转发
我可以想到的第三种方法是仅将
哪种方法是正确的?也许还有其他方法我完全没有想到?
谢谢。
expected<E, T>
,但遇到了问题。在描述单子功能(5.9)时,在绑定时指出,如果结果已经包含在上下文(expected<E, T>
)中,则不应再次包装。我实现的方式是,绑定有两个重载(使用
enable_if
),一个用于返回expected
实例的函子,实现没有在上下文中包装它,另一个用于返回其他类型的函子,它会在上下文中包装它。我遇到了一个问题,非包装版本在调用者中没有值的情况下必须返回一个默认构造的expected<E1, T1>
,这给了默认构造的错误值。这导致返回的expected的进一步连续失去了导致默认构造的错误的上下文。
也许我应该处理被称为
is_same<expected<E,T>, functor_ret_type>
的上下文,在调用者中出现错误的情况下,我可以转发“this”并保留错误的上下文,但这将导致返回expected<E1, E2>
的函子返回expected<E, expected<E1, E2>>
假设该类具有以下特点:E& error(); //returns the stored error
T& operator*(); //returns a reference to the stored value
bool has_value(); //returns true if the expected value is present, false if the error is present
以下是我最初的实施方式:
这里是我最初的实现方式:
//overload for wrapping functors
template<typename Functor>
auto bind(Functor functor) -> std::enable_if<is_instance<expected,
decltype(functor(**this))>::value,
decltype(functor(**this))>::type
{
using result_type = decltype(functor(**this));
if (this->has_value())
{
return functor(**this);
}
return result_type();
}
//overload for non wrapping functors
template<typename Functor>
auto bind(Functor functor) -> std::enable_if<!is_instance<expected,
decltype(functor(**this))>::value,
expected<E, decltype(functor(**this))>>::type
{
using result_type = decltype(functor(**this));
if (has_value())
{
return { functor(**this) };
}
return expected<E, result_type>(this->error());
}
在第一个重载中,如果没有值,我们会返回一个默认构造的expected<E, T>
。该类型是functor
返回的类型,其中包含一个默认构造的错误类型E
,这使得我们由于未调用函数而失去了原始错误的上下文。
如果我将上述行为解释为“如果functor返回与调用绑定的相同类型的expected<E, T>
,则不进行封装;否则进行封装”,我们可以有以下实现:
//overload for wrapping functors
template<typename Functor>
auto bind(Functor functor) -> std::enable_if<is_same<expected<E, T>,
decltype(functor(**this))>::value,
decltype(functor(**this))>::type
{
if (this->has_value())
{
return functor(**this);
}
return *this;
}
//overload for non wrapping functors
template<typename Functor>
auto bind(Functor functor) -> std::enable_if<!is_same<expected<E, T>,
decltype(functor(**this))>::value,
expected<E, decltype(functor(**this))>>::type
{
using result_type = decltype(functor(**this));
if (has_value())
{
return { functor(**this) };
}
return expected<E, result_type>(this->error());
}
在这里,如果没有值存在于包装的重载中,我们会转发
this
,这使得我们能够知道最初的错误是什么,但是如果函数返回expected<E1, T1>
,则结果将是被包装的expected<E, expected<E1, T1>>
。我可以想到的第三种方法是仅将
E
视为上下文,这会稍微不那么严格,并允许解开返回expected<E, T1>
的函数对象,但对于expected<E1, T1>
的问题仍然存在。哪种方法是正确的?也许还有其他方法我完全没有想到?
谢谢。
**this
应该做什么? - BЈовић