C++ 向量置换解析器<;bool>;,通过火柴
在我的boost中,我有以下规则::spirit语法C++ 向量置换解析器<;bool>;,通过火柴,c++,boost-spirit,boost-spirit-qi,C++,Boost Spirit,Boost Spirit Qi,在我的boost中,我有以下规则::spirit语法 rule = (qi::token(ABSTRACT) ^ qi::token(STATIC) ^ qi::token(FINAL)) 该结构具有以下类型: boost::fusion::vector3<boost::optional<boost::iterator_range<std::string::iterator>>, boost::optional<boost::iterator_range&l
rule = (qi::token(ABSTRACT) ^ qi::token(STATIC) ^ qi::token(FINAL))
该结构具有以下类型:
boost::fusion::vector3<boost::optional<boost::iterator_range<std::string::iterator>>, boost::optional<boost::iterator_range<std::string::iterator>>, boost::optional<boost::iterator_range<std::string::iterator>>>
哪一个有类型
boost::fusion::vector3<boost::optional<bool>, boost::optional<bool>, boost::optional<bool>>
boost::fusion::vector3
这确实不是我想要的,那么我该怎么做,以随机顺序匹配这三个标记,并得到它们是否匹配为布尔值?我假设你并不真的需要一个
fusion::vector
,你只是想让它工作。如果这个假设是错误的,只需在评论中说些什么
如图所示,置换解析器的属性为
tuple@P0W这是一个boost fusion向量,而不是您希望避免bools的std::vector
。我猜缺少一些上下文?置换解析器的属性将始终是fusion::vector
。我认为这个向量应该与fusion::vector
兼容(它应该将每个非空的可选项分配给相应的元素)。我看到您的代码存在的问题是,qi::matches
总是成功的,因此我认为只有当这三个关键字都存在并且顺序正确时,您的代码才能工作。@Skeen注意,在我的“艺术家印象”(artist impression)中,我显示了。@sehe应该是。。。习惯性地将此作为回答;)我使用了一些与显式属性方法类似的方法。
(qi::matches[qi::raw_token(ABSTRACT)] ^ qi::matches[qi::raw_token(STATIC)] ^ qi::matches[qi::raw_token(FINAL)])
boost::fusion::vector3<boost::optional<bool>, boost::optional<bool>, boost::optional<bool>>
USING MATCHES: final abstract static
<abstract1>
<try>final abstract stati</try>
<success>final abstract stati</success>
<attributes>[0]</attributes>
</abstract1>
<static1>
<try>final abstract stati</try>
<success>final abstract stati</success>
<attributes>[0]</attributes>
</static1>
<final1>
<try>final abstract stati</try>
<success> abstract static</success>
<attributes>[1]</attributes>
</final1>
#include <iostream>
#include <string>
#include <vector>
#define BOOST_SPIRIT_DEBUG
#include <boost/spirit/include/qi.hpp>
#include <boost/fusion/include/adapt_struct.hpp>
struct class_info
{
class_info():abstract_(),static_(),final_(){}
bool abstract_;
bool static_;
bool final_;
};
BOOST_FUSION_ADAPT_STRUCT
(
class_info,
(bool, abstract_)
(bool, static_)
(bool, final_)
)
namespace qi=boost::spirit::qi;
template <typename Parser>
void parse_triplet(const std::string& test, const Parser& parser)
{
std::string::const_iterator iter=test.begin(), end=test.end();
class_info parsed_class;
bool result=qi::phrase_parse(iter,end,parser,qi::space,parsed_class);
if(!result)
{
std::cout << "The triplet could not be parsed. Unparsed: " << std::string(iter,end) << std::endl;
}
else
{
if(iter==end)
{
std::cout << "A triplet was parsed." << std::endl;
std::cout << parsed_class.abstract_ << parsed_class.static_ << parsed_class.final_ << std::endl;
}
else
{
std::cout << "A triplet was parsed, but part of the input remained unparsed." << std::endl;
std::cout << parsed_class.abstract_ << parsed_class.static_ << parsed_class.final_ << std::endl;
std::cout << "Unparsed: " << std::string(iter,end) << std::endl;
}
}
}
int main()
{
std::vector<std::string> tests;
tests.push_back("final abstract static");
tests.push_back("final abstract");
tests.push_back("static");
tests.push_back("static abstract");
qi::rule<std::string::const_iterator,bool(),qi::space_type> abstract1, abstract2, static1, static2, final1, final2;
abstract1 = qi::matches[qi::lit("abstract")];
abstract2 = qi::lit("abstract") >> qi::attr(true);
static1 = qi::matches[qi::lit("static")];
static2 = qi::lit("static") >> qi::attr(true);
final1 = qi::matches[qi::lit("final")];
final2 = qi::lit("final") >> qi::attr(true);
BOOST_SPIRIT_DEBUG_NODES( (abstract1)(abstract2)(static1)(static2)(final1)(final2) );
for(std::size_t cont=0; cont < tests.size(); ++cont)
{
//THIS IS WRONG
std::cout << "USING MATCHES: " << tests[cont] << std::endl;
parse_triplet(tests[cont],abstract1 ^ static1 ^ final1);
//THIS WORKS
std::cout << "USING EXPLICIT ATTRIBUTE: " << tests[cont] << std::endl;
parse_triplet(tests[cont],abstract2 ^ static2 ^ final2);
}
}