为什么不赞成使用boost :: optional :: is_initialized()?

时间:2017-05-23 06:47:56

标签: c++ boost optional

我今天注意到boost::optional::is_initialized()已将is_initialized()标记为已弃用。我的项目充满了boost::optional以检查boost::optional是否包含值。

我没有看到任何其他方法来正确测试boost::optional是否已初始化,我是否遗漏了某些内容?

explicit operator bool()有一个if(foo){...},这意味着如果fooboost::optional,我可以foo。但是,如果boost::optional<bool>boost::optional<T>或其他T bool可转换为colums => location, ltn,lgn,则会产生错误的结果。

Boost期望用户做什么?

3 个答案:

答案 0 :(得分:8)

  

然而,如果foo是boost :: optional或其他一些boost :: optional,其中T可以转换为bool,那么这会产生错误的结果。

不,因为没有隐式转换为基础类型。可选总是的“真实性”¹指的是其初始化状态。

您可能获得隐式转换的展示的唯一时间是关系运算符。但是,这并没有隐式转换为基础类型,而是明确地提升运算符。

¹我指的是上下文(显式)布尔转换

更新

确实boost::optional<bool>有警告in pre-c++11 mode

  

其次,虽然可选&lt;&gt;在C ++ 11中提供了对bool的上下文转换,这可以追溯到旧编译器的隐式转换

在这种情况下,明确地与boost::none进行比较显然更好。

答案 1 :(得分:1)

在撰写本文时,Boost 1.72支持“ has_value”方法,该方法尚未弃用。

在后台,它只是调用“ is_initialized”。 参见the code

/album...
/album...
/album...

此外,我看到的另一个方便的技巧是bool has_value() const BOOST_NOEXCEPT { return this->is_initialized() ; } 惯用语。 例如:

!!

与写boost::optional<Foo> x = ... MY_ASSERT(!!x, "x must be set"); 或更冗长的(bool)x基本相同。

此外:不推荐使用static_cast<bool>(x),这有点奇怪,后来又添加了一个具有不同名称的完全等效的函数。我怀疑这是为了与C ++ 17的std::optional兼容。

答案 2 :(得分:0)

对于将来的引用,如on boost documentation所述,您可以从现在开始进行如下比较:

boost::optional<int> oN = boost::none;
boost::optional<int> o0 = 0;
boost::optional<int> o1 = 1;

assert(oN != o0);
assert(o1 != oN);
assert(o0 != o1);
assert(oN == oN);
assert(o0 == o0);

您甚至可以:

if(oN != 2){}

或只是检查该值是否已设置:

if(oN){}