Calling a function or functor using a sprit parsing library rule to store values โ€‹โ€‹in a C ++ vector

I want to parse this line and store all the hex values โ€‹โ€‹in a functor <005F> <0061> [<00660066> <00660069> <00660066006C>] these values โ€‹โ€‹in a txt file and m reading this line fill with a string

like 005F 0061 00660066 00660069 00660066006C all values โ€‹โ€‹should be in vector but not work

spirit's rule is to parse this line:

rule<> blanks = *blank_p;
rule<> parse_int = blanks >> "<" >> int_p [AddEntry] >> ">";
rule<> parse_ints = *parse_int ;
rule<> parse_range = *parse_int >>"[" >> blanks >> *parse_int >> "]";

int status = parse (line.c_str(),
*(
     parse_range 
 )
 ).full;

      

and my functor is

struct AddEntry
{
    vector<int> list;   
    void operator()( int integer)
    {
        list.push_back(integer);
    }
};

      

+3


source to share


1 answer


Here's an example using Spirit V2

Live On Coliru

#define BOOST_SPIRIT_DEBUG
#include <boost/spirit/include/qi.hpp>
namespace qi  = boost::spirit::qi;

int main() {
    typedef std::string::const_iterator It;
    std::string const line = "<005F> <0061> [<00660066> <00660069> <00660066006C>]";

    It f = line.begin(), l = line.end();

    qi::int_parser<uintmax_t, 16> hex_int;
    qi::rule<It, uintmax_t()> braced_hex = '<' >> hex_int >> '>';
    BOOST_SPIRIT_DEBUG_NODE(braced_hex);

    std::vector<uintmax_t> list;
    bool result = qi::phrase_parse(f, l, *braced_hex >> '[' >> *braced_hex >> ']', qi::space, list);

    if (result) {
        std::cout << "Parse success: " << list.size() << "\n";

        for (auto& v : list)
            std::cout << v << " ";
    }
    else {
        std::cout << "Parse failed\n";
    }

    if (f!=l) {
        std::cout << "Remaining unparsed: '" << std::string(f,l) << "'\n";
    }
}

      

Output:

Parse success: 5
95 97 6684774 6684777 438093348972 

      

Debug output (if enabled):



<braced_hex>
    <try><005F> <0061> [<0066</try>
    <success> <0061> [<00660066> </success>
    <attributes>[95]</attributes>
</braced_hex>
<braced_hex>
    <try><0061> [<00660066> <</try>
    <success> [<00660066> <006600</success>
    <attributes>[97]</attributes>
</braced_hex>
<braced_hex>
    <try>[<00660066> <0066006</try>
    <fail/>
</braced_hex>
<braced_hex>
    <try><00660066> <00660069</try>
    <success> <00660069> <0066006</success>
    <attributes>[6684774]</attributes>
</braced_hex>
<braced_hex>
    <try><00660069> <00660066</try>
    <success> <00660066006C>]</success>
    <attributes>[6684777]</attributes>
</braced_hex>
<braced_hex>
    <try><00660066006C>]</try>
    <success>]</success>
    <attributes>[438093348972]</attributes>
</braced_hex>
<braced_hex>
    <try>]</try>
    <fail/>
</braced_hex>

      

Note that my system is int

not large enough to hold these numbers, so parsing will fail. For the maximum range I used intmax_t

, but you can use other types, including arbitrary precision types:

Also note that I prefer not to use semantic actions, using automatic attribute propagation. This is really common in Spirit V2. See also

+2


source







All Articles