是否无法继承boost :: variant并将结果类用作选择运算符结果?
struct jass_statement_node {
};
typedef boost::variant<
boost::recursive_wrapper<jass_set>
, boost::recursive_wrapper<jass_call>
, boost::recursive_wrapper<jass_ifthenelse>
, boost::recursive_wrapper<jass_loop>
, boost::recursive_wrapper<jass_exitwhen>
, boost::recursive_wrapper<jass_return>
, boost::recursive_wrapper<jass_debug>
> jass_statement_base;
struct jass_statement : public jass_statement_node, public jass_statement_base {
};
...
statement %=
set
| call
| ifthenelse
| loop
| exitwhen
| return_statement
| debug
;
会导致attr_cast错误。如果我使用base作为属性它可以工作,但我必须调整结构:
struct jass_statement : public jass_statement_node {
jass_statement_base value;
};
BOOST_FUSION_ADAPT_STRUCT(
jass_statement,
(jass_statement_base, value)
)
答案 0 :(得分:1)
快速检查
#include <boost/spirit/include/qi.hpp>
using V = boost::variant<int, double, std::string>;
struct my_struct : V {
};
int main()
{
std::string const input("3.14151926");
auto f(begin(input)), l(end(input));
using namespace boost::spirit::qi;
V parsed;
bool ok = phrase_parse(
f, l,
lexeme [ '"' >> *~char_('"') >> '"' ] // string
| real_parser<double, strict_real_policies<double> >() // double
| int_ // well, int :)
, space, parsed);
return ok? 1 : 2;
}
确认这确实不是问题。因此,它与其他规则与变体元素类型的精确兼容性有关。
您可以专门为您的类型分配/转换特征:
namespace boost { namespace spirit { namespace traits {
template <typename Exposed, typename Domain>
struct transform_attribute<Exposed, my_struct, Domain, void> :
transform_attribute<Exposed, V, Domain, void> {
using base_type = transform_attribute<Exposed, V, Domain, void>;
using typename base_type::type;
//static type pre(Exposed& val) { return base_type::pre(val); }
//static void post(Exposed& val, type attr) { base_type::post(val, attr); }
//static void fail(Exposed&e) { base_type::fail(e); }
};
} } }
你可以试试这个(我希望这次没有让Exposed
和Transformed
再次混淆:))
请参阅上面的 Live On Coliru