std :: optional枚举的比较运算符

时间:2018-10-21 17:09:49

标签: c++ c++17 optional comparison-operators

根据this,在optional<T>和{{1}上定义比较运算符的前提下,应该在optional<U>T上使用比较运算符}}。

我正在尝试下面的示例,其中在不同的命名空间(实时代码here)中定义了两个枚举,但无法弄清楚为什么它无法编译:

U

我的GCC-8.2.0说:

#include <optional> namespace n1 { enum class tag : unsigned {I,II,III}; } namespace n2 { enum class tag : unsigned {I,II,III}; } bool operator<(const n1::tag& t1, const n2::tag& t2) { return static_cast<unsigned>(t1) < static_cast<unsigned>(t2); } int main() { const std::optional<n1::tag> o1(n1::tag::I); const std::optional<n2::tag> o2(n2::tag::I); bool t = (o1 < o2); }

有什么想法吗?我发现将每个枚举移出其命名空间后,一切都会按预期进行(如here)。

1 个答案:

答案 0 :(得分:7)

<运算符必须位于它的参数的任何关联命名空间中,即它必须位于命名空间n1n2中,但由于n2::tag不可见在n1::tag的定义中,您需要将运算符放在命名空间n2中或重新打开命名空间n1

在命名空间n2中定义运算符:

namespace n2
{
    enum class tag : unsigned {I,II,III};
    bool operator<(const n1::tag& t1, const n2::tag& t2)
    {
        return static_cast<unsigned>(t1) < static_cast<unsigned>(t2);
    }    
}

打开命名空间n1

...

namespace n2
{
    enum class tag : unsigned {I,II,III};
}
namespace n1 {
    bool operator<(const n1::tag& t1, const n2::tag& t2)
    {
        return static_cast<unsigned>(t1) < static_cast<unsigned>(t2);
    }        
}