Search code examples
c++boostboost-propertytree

boost ptree access first element with no path name


I am using boost library to manipulate a JSON string and I would like to access to a first element.

I was wondering if there where some convenient way to access a first element of ptree with no path name.

I do this, but I got no value :

namespace pt = boost::property_tree;
pt::ptree pt2;
string json = "\"ok\"";
istringstream is(json);
try
{
        pt::read_json(is, pt2);
        cout << pt2.get_child("").equal_range("").first->first.data() << endl;
}
catch (std::exception const& e)
{
        cerr << e.what() << endl;
}

Solution:

replace cout << pt2.get_child("").equal_range("").first->first.data() << endl;

by cout << pt2.get_value<std::string>() << endl;


Solution

  • Firstly, Property Tree is not a JSON library.

    Secondly, the input is not in the subset of JSON supported by the library (e.g.).

    Thirdly, since the input results in a tree that has no child nodes, you should use the value of the root node itself.

    Lastly, if you had wanted the first node, use ordered_begin()->second:

    Live On Coliru

    #include <boost/property_tree/json_parser.hpp>
    #include <boost/property_tree/xml_parser.hpp>
    #include <iostream>
    
    void broken_input() {
        boost::property_tree::ptree pt;
        std::istringstream is("\"ok\"");
        read_json(is, pt);
        std::cout << "Root value is " << pt.get_value<std::string>() << std::endl;
    }
    
    void normal_tree() {
        boost::property_tree::ptree pt;
        pt.put("first", "hello");
        pt.put("second", "world");
        pt.put("third", "bye");
    
        std::cout << pt.ordered_begin()->second.get_value<std::string>() << std::endl;
    
        write_json(std::cout, pt);
    }
    
    
    int main() {
        try {
            broken_input();
            normal_tree();
        }
        catch (std::exception const& e)
        {
            std::cerr << e.what() << std::endl;
        }
    }
    

    Prints

    Root value is ok
    hello
    {
        "first": "hello",
        "second": "world",
        "third": "bye"
    }