Spirit: parsing tab separated values and no_skip compilation error.
Hi, I am a beginner with Spirit. I just read the tutorial and I am playing around with some examples. Environment: boost 1.43, Windows Vista, Code::Blocks, mingw, gcc 4.5. My goal is to build a tab separated values parser. If you have an example on how to parse something like: string/t/tdouble/tdouble it would be great. Contiguous tabs should be considered as one tab, not an empty field. To start I just tried to parse a tab separated list of strings but I am having some difficulties. Is there another skip parser to be used instead of space (for full code see the end of the message below) ? I have changed the commas to tabs in the code below but it failed. I guess it was because it was skipping them (space skipper). bool r = phrase_parse(first, last, // Begin grammar ( +(char_ - ',') % ',' ) , // End grammar space, v); This code works with commas but it fails with '\t'. I tried to use no_skip[] but it failed to compile the header #include <boost/spirit/include/qi_no_skip.hpp>: C:\boost_1_43_0\boost\spirit\home\qi\directive\no_skip.hpp|30|error: 'no_skip' is not a member of 'boost::spirit::tag'| For full error message see the end of the message below. Any suggestions ? Thank you for your attention, Mau. #include <boost/config/warning_disable.hpp> #include <boost/spirit/include/qi.hpp> #include <boost/spirit/include/phoenix_core.hpp> #include <boost/spirit/include/phoenix_operator.hpp> #include <boost/spirit/include/phoenix_stl.hpp> //#include <boost/spirit/include/qi_no_skip.hpp> #include <iostream> #include <string> #include <vector> #define VECTOR_TYPE std::string namespace client { namespace qi = boost::spirit::qi; namespace ascii = boost::spirit::ascii; /////////////////////////////////////////////////////////////////////////// // Our number list compiler /////////////////////////////////////////////////////////////////////////// //[tutorial_numlist4 template <typename Iterator> bool parse_numbers(Iterator first, Iterator last, std::vector<VECTOR_TYPE>& v) { using qi::double_; using qi::phrase_parse; using qi::_1; using ascii::space; using qi::char_; bool r = phrase_parse(first, last, // Begin grammar ( +(char_ - ',') % ',' ) , // End grammar space, v); if (first != last) // fail if we did not get a full match return false; return r; } //] } //////////////////////////////////////////////////////////////////////////// // Main program //////////////////////////////////////////////////////////////////////////// int main() { std::cout << "/////////////////////////////////////////////////////////\n\n"; std::cout << "\t\tA comma separated list parser for Spirit...\n\n"; std::cout << "/////////////////////////////////////////////////////////\n\n"; std::cout << "Give me a comma separated list of numbers.\n"; std::cout << "The numbers will be inserted in a vector of numbers\n"; std::cout << "Type [q or Q] to quit\n\n"; std::string str; while (getline(std::cin, str)) { if (str.empty() || str[0] == 'q' || str[0] == 'Q') break; std::vector<VECTOR_TYPE> v; if (client::parse_numbers(str.begin(), str.end(), v)) { std::cout << "-------------------------\n"; std::cout << "Parsing succeeded\n"; std::cout << str << " Parses OK: " << std::endl; for (std::vector<VECTOR_TYPE>::size_type i = 0; i < v.size(); ++i) std::cout << i << ": " << v[i] << std::endl; std::cout << "\n-------------------------\n"; } else { std::cout << "-------------------------\n"; std::cout << "Parsing failed\n"; std::cout << "-------------------------\n"; } } std::cout << "Bye... :-) \n\n"; return 0; } Error messages when compiling with the no_skip include file: C:\boost_1_43_0\boost\spirit\home\qi\directive\no_skip.hpp|30|error: 'no_skip' is not a member of 'boost::spirit::tag'| C:\boost_1_43_0\boost\spirit\home\qi\directive\no_skip.hpp|30|error: 'no_skip' is not a member of 'boost::spirit::tag'| C:\boost_1_43_0\boost\spirit\home\qi\directive\no_skip.hpp|30|error: template argument 2 is invalid| C:\boost_1_43_0\boost\spirit\home\qi\directive\no_skip.hpp|36|error: 'boost::spirit::no_skip' has not been declared| C:\boost_1_43_0\boost\spirit\home\qi\directive\no_skip.hpp|37|error: 'boost::spirit::no_skip_type' has not been declared| C:\boost_1_43_0\boost\spirit\home\qi\directive\no_skip.hpp|79|error: 'no_skip' is not a member of 'boost::spirit::tag'| C:\boost_1_43_0\boost\spirit\home\qi\directive\no_skip.hpp|79|error: 'no_skip' is not a member of 'boost::spirit::tag'| C:\boost_1_43_0\boost\spirit\home\qi\directive\no_skip.hpp|79|error: template argument 1 is invalid| ||=== Build finished: 8 errors, 0 warnings ===| -- Mauricio Gomes Pensar Digital 55-11-9698-1683 (Brazil - mobile)
I am a beginner with Spirit. I just read the tutorial and I am playing around with some examples. Environment: boost 1.43, Windows Vista, Code::Blocks, mingw, gcc 4.5.
My goal is to build a tab separated values parser. If you have an example on how to parse something like: string/t/tdouble/tdouble it would be great. Contiguous tabs should be considered as one tab, not an empty field.
To start I just tried to parse a tab separated list of strings but I am having some difficulties.
Is there another skip parser to be used instead of space (for full code see the end of the message below) ? I have changed the commas to tabs in the code below but it failed. I guess it was because it was skipping them (space skipper).
bool r = phrase_parse(first, last,
// Begin grammar ( +(char_ - ',') % ',' ) , // End grammar
space, v);
This code works with commas but it fails with '\t'.
I tried to use no_skip[] but it failed to compile the header #include <boost/spirit/include/qi_no_skip.hpp>:
C:\boost_1_43_0\boost\spirit\home\qi\directive\no_skip.hpp|30|error: 'no_skip' is not a member of 'boost::spirit::tag'|
For full error message see the end of the message below.
Any suggestions ?
Thank you for your attention, Mau.
#include <boost/config/warning_disable.hpp> #include <boost/spirit/include/qi.hpp> #include <boost/spirit/include/phoenix_core.hpp> #include <boost/spirit/include/phoenix_operator.hpp> #include <boost/spirit/include/phoenix_stl.hpp> //#include <boost/spirit/include/qi_no_skip.hpp>
#include <iostream> #include <string> #include <vector>
#define VECTOR_TYPE std::string
namespace client { namespace qi = boost::spirit::qi; namespace ascii = boost::spirit::ascii;
////////////////////////////////////////////////////////////////////// ///// // Our number list compiler ////////////////////////////////////////////////////////////////////// ///// //[tutorial_numlist4 template <typename Iterator> bool parse_numbers(Iterator first, Iterator last, std::vector<VECTOR_TYPE>& v) { using qi::double_; using qi::phrase_parse; using qi::_1; using ascii::space; using qi::char_;
bool r = phrase_parse(first, last,
// Begin grammar ( +(char_ - ',') % ',' ) , // End grammar
space, v);
if (first != last) // fail if we did not get a full match return false; return r; } //] }
////////////////////////////////////////////////////////////////////////// // // Main program ////////////////////////////////////////////////////////////////////////// // int main() { std::cout << "/////////////////////////////////////////////////////////\n\n"; std::cout << "\t\tA comma separated list parser for Spirit...\n\n"; std::cout << "/////////////////////////////////////////////////////////\n\n";
std::cout << "Give me a comma separated list of numbers.\n"; std::cout << "The numbers will be inserted in a vector of numbers\n"; std::cout << "Type [q or Q] to quit\n\n";
std::string str; while (getline(std::cin, str)) { if (str.empty() || str[0] == 'q' || str[0] == 'Q') break;
std::vector<VECTOR_TYPE> v; if (client::parse_numbers(str.begin(), str.end(), v)) { std::cout << "-------------------------\n"; std::cout << "Parsing succeeded\n"; std::cout << str << " Parses OK: " << std::endl;
for (std::vector<VECTOR_TYPE>::size_type i = 0; i < v.size(); ++i) std::cout << i << ": " << v[i] << std::endl;
std::cout << "\n-------------------------\n"; } else { std::cout << "-------------------------\n"; std::cout << "Parsing failed\n"; std::cout << "-------------------------\n"; } }
std::cout << "Bye... :-) \n\n"; return 0; }
This example compiles fine for me (VC10, g++ 4.5). Is it supposed to fail? Regards Hartmut --------------- Meet me at BoostCon www.boostcon.com
participants (2)
-
Hartmut Kaiser
-
Mauricio Gomes