【问题标题】:Boost PropertyTree: check if child existsBoost PropertyTree:检查孩子是否存在
【发布时间】:2011-11-25 23:38:24
【问题描述】:

我正在尝试编写一个 XML 解析器,将 XML 文件解析为 boost::property_tree 并遇到了这个问题。如何(快速)检查某个属性的子对象是否存在?

显然,我可以使用 BOOST_FOREACH 遍历所有孩子 - 但是,没有更好的解决方案吗?

【问题讨论】:

    标签: c++ boost boost-propertytree


    【解决方案1】:
    optional< const ptree& > child = node.get_child_optional( "possibly_missing_node" );
    if( !child )
    {
      // child node is missing
    }
    

    【讨论】:

    • 为了让您的示例正常工作,我必须删除 'const' - 你能解释一下为什么在这里使用 'const' 吗?
    • 为了安全。读取配置时,几乎没有理由修改值。快速搜索显示 ptree 仍然(在 boost 1.61.0 中)有一个 get_child_optional 重载,它返回 optional,因此您的错误将与您随后对该值所做的操作有关。
    • 我尝试了几种替代方法,最终使用了 boost::optional。请注意,您还可以使用 Boost 文档中的代码直接访问数据:请参阅 Boost docs here。试试这个: boost::optional v = pt.get_optional("a.path.to.float.value");
    【解决方案2】:

    这里有几个其他的选择:

    if( node.count("possibliy_missing") == 0 )
    {
       ...
    }
    
    ptree::const_assoc_iterator it = ptree.find("possibly_missing");
    if( it == ptree.not_found() )
    {
       ...
    }
    

    【讨论】:

    • 我喜欢第二个...更多stl风格
    • 我发现有趣的是,与 get 方法不同,find 方法不提供对 find("SubNode.Attribute") 的支持。您必须手动获取 ptree 中的 SubNode 子节点并在子实例上运行 find,
    • node.count 也不适用于嵌套键,例如“child.subchild”。到目前为止,我发现唯一有效的是 node.get_child_optional,如下面的答案stackoverflow.com/a/25389349/844728
    【解决方案3】:

    包括这个:

    #include <boost/optional/optional.hpp>
    

    删除const:

    boost::optional< ptree& > child = node.get_child_optional( "possibly_missing_node" );
    if( !child )
    {
      // child node is missing
    }
    

    【讨论】:

    • 虽然您的答案有效,但您复制了大部分已被接受且已有近 3 年历史的另一个答案(没有披露!)。你能至少解释一下你为什么做出你所做的改变吗?这可能更适合作为评论。
    • 我投了反对票,因为你没有添加到解决方案中 - 也许如果你改变的不仅仅是删除 const,那么我会投赞成票
    【解决方案4】:

    虽然这些解决方案似乎可以避免在树上进行迭代,但请记住,在幕后他们仍在这样做,因此您正在使您的算法潜在地 n^2... 如果您担心性能和有多余的内存,您可以使用地图容器进行快速查找。

    【讨论】:

    • 听起来很有趣——也许你可以写一个小例子?
    【解决方案5】:

    可以使用的另一种方法是在您不想检查某些潜在的丢失子/节点的情况下使用。尝试使用迭代器:

    if (node.begin() != node.end()) { // Node does have child[ren]
         // Code to process child nodes
    }
    

    【讨论】:

      猜你喜欢
      • 2017-10-24
      • 2016-09-18
      • 2016-09-20
      • 2010-12-06
      • 2013-05-09
      • 1970-01-01
      • 2017-02-25
      • 2017-04-27
      • 1970-01-01
      相关资源
      最近更新 更多