促进property_tree问题获取价值

时间:2018-09-25 15:44:36

标签: c++ boost boost-propertytree

这是我对boost :: property_tree的首次体验,我找不到遵循文档(How to Access Data in a Property Tree)重现从树中获取值的方法。这是我编写的用于尝试使用属性树的简单代码:

#include <iostream>
#include <string>

#include <boost/property_tree/info_parser.hpp>
#include <boost/property_tree/ptree.hpp>

namespace pt = boost::property_tree;

int main(int argc, char *argv[]) {
  pt::ptree tree;

  tree.put("pi", 3.14159);
  tree.put("name", "John Doe");

  for (auto &[key, value] : tree)
    std::cout << key << " : " << value.get_value<std::string>() << "\n";

  std::cout << "pi : " << tree.get_value("pi") << "\n";
  std::cout << "name : " << tree.get_value("name") << "\n";

  auto pi = tree.get_optional<float>("pi").get();
  std::cout << "pi optional : " << pi << "\n";

  auto pi_found = tree.find("pi");
  std::cout << "pi found : " << pi_found->second.data() << "\n";

  // the commented line doesn't compile
  // std::cout << "not found : " << tree.get_value<int>("null") << "\n";

  std::cout << "not found : " << tree.get_value("null") << "\n";

  // the line below causes an assertion error:
  // Assertion failed: (this->is_initialized()), function get, file /usr/local/include/boost/optional/optional.hpp, line 1191.
  // not found : Abort trap: 6
  std::cout << "not found : " << tree.get_optional<int>("null").get() << "\n";

  pt::write_info("ptree.info", tree);

  return 0;
}

这是输出:

pi : 3.1415899999999999
name : John Doe
pi :
name :
pi optional : 3.14159
pi found : 3.1415899999999999
not found :

可以看出,tree.get_value("whatever")不返回任何值,tree.get_value("null")不会引发异常,get_optional<whatever type>也不会编译。我的实验与文档中所述的行为有很大不同。排除导致断言错误的行,将按预期创建输出信息文件。

我的环境是:

MacOS 10.11.6
macbrew installed tools and libraries
boost 1.67
clang 7.0
meson build system

2 个答案:

答案 0 :(得分:1)

您可以将ptree绘制为:

node1 is tree (has 2 children, data() of tree is "")
 |
 |- (node2) pi ----> data=3.14...
 |
 |- (node3) name --> data="Joe Doe"

[1]

  

可以看出tree.get_value(“ whatever”)不返回任何值

tree是节点,有2个子节点(pi,名称)。 通话时

tree.get_value(defaultValue) // you are not passing PATH, but DEFAULT VALUE

以上行被翻译为

tree.get_child("").get_value(defaultValue)

因此,存在""路径,因为它是到tree节点的路径,并且tree.data()返回""-此路径的空字符串。因此defaultValue无法打印,并且您会看到空字符串作为输出。 您应该只为孩子调用get_value(在调用此方法之前,请在get_child上使用tree,在boost参考中对此进行了描述),并且get_value的参数是默认值。因此,替换

  std::cout << "pi : " << tree.get_child("pi").get_value("PI is 4.0") << "\n";
  std::cout << "name : " << tree.get_child("name").get_value("noname") << "\n";

您将看到3.14Joe Doe

[2]

  

tree.get_value(“ null”)不会引发异常

在[1]中描述了

""路径存在,并且此路径的data()是空字符串。因此,您无法看到null字符串作为默认值。

[3]

  

//注释行无法编译// std :: cout <<“ not found:”

     

<< tree.get_value(“ null”)<<“ \ n”;

由于ptree类没有该方法,因此无法编译此行,我想您要调用此方法:

  template<typename Type> 
  unspecified get_value(const Type & default_value) const;

您将Type定义为intint定义为函数模板参数,因为该参数涉及默认值只能是int,而不能是字符串。

答案 1 :(得分:0)

我很糟糕,我没有使用tree.get<float>("pi"),而是复制并粘贴了tree.get_value<float>("pi"),这是为其他用途。在@ rafix07评论的帮助下回答了该问题。 get<type>("key path")是正确的使用方法。