考虑以下 XML 文件:
<debug>
<modules group="0">
<module>Finance</module>
<module>Admin</module>
<module>HR</module>
</modules>
</debug>
使用 Boost.PropertyTree 可以遍历节点的子节点:
BOOST_FOREACH(ptree::value_type &v, pt.get_child("debug.modules"))
{
}
但由于属性也被视为子项,因此“模块”的第一个子项将是“组”而不是“模块”。 有没有办法只选择属性树的子节点? 一种可能性是检查
if(v.first == "module")
但是有没有更好的办法呢?
最佳答案
您可以使用 equal_range()
property_tree
上的成员函数,它返回 std::pair
迭代器,用特定键标记一系列子节点。然后你可以使用Boost Range在范围内操作。
这与 C++11 的 auto
类型说明符和基于范围的 for 循环(或 BOOST_AUTO
和 BOOST_FOREACH
)配合得很好:
#include <iostream>
#include <sstream>
#include <boost/property_tree/ptree.hpp>
#include <boost/property_tree/xml_parser.hpp>
#include <boost/range/iterator_range.hpp>
static const std::string input =
"<debug>"
" <modules group=\"0\">"
" <module>Finance</module>"
" <module>Admin</module>"
" <module>HR</module>"
" </modules>"
"</debug>";
int main() {
std::istringstream istream(input);
boost::property_tree::ptree ptree;
boost::property_tree::read_xml(istream, ptree);
const auto range = ptree.get_child("debug.modules").equal_range("module");
for (auto& child : boost::make_iterator_range(range)) {
std::cout << child.first << std::endl;
}
return 0;
}
这在算法上比检查每个 child 要好,尽管我怀疑它在普通用法中有多大区别。
关于c++ - 只选择 Boost ptree 的节点,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/37886341/