Il codice seguente è una versione semplificata di ciò che sto tentando di fare. Fondamentalmente, ho struct (int_holder nel codice del giocattolo), con un membro di dati del contenitore. Voglio inserire un oggetto (int in questo caso) e restituire al genitore qi :: rule un puntatore all'oggetto appena inserito.spirit :: qi: passaggio attributo ereditato riferimento a phoenix :: function
Ho passato l'int_holder alla grammatica per riferimento, per riempirlo di valori durante l'analisi, quindi int_holder sarà un attributo ereditato della grammatica. Codice:
#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_function.hpp>
#include <vector>
namespace qi=boost::spirit::qi;
namespace phoenix=boost::phoenix;
struct int_holder
{
int_holder() {}
std::vector<int> ints;
};
struct insert_impl
{
template<class, class>
struct result { typedef int* type; };
int* operator() (int_holder& holder, int i) const
{
holder.ints.push_back (i);
return &holder.ints.back();
}
};
template<class Iterator>
struct my_grammar : qi::grammar<Iterator, int*(int_holder&)>
{
my_grammar() : my_grammar::base_type (start)
, insert (insert_impl())
{
using qi::_val;
using qi::int_;
using qi::_r1;
using qi::_1;
using phoenix::ref;
start = +next(_val) [_val = _1];
next = int_ [_val = insert(_r1, _1)];
}
qi::rule<Iterator, int*(int_holder&)> start, next;
phoenix::function<insert_impl> insert;
};
int main()
{
using phoenix::ref;
const char* p="1";
int* last;
int_holder holder;
my_grammar<const char*> g;
qi::parse (p, p+1, g(ref(holder)), last);
}
Il codice non si compila, con il seguente messaggio di errore:
In file included from
/opt/local/include/boost/fusion/sequence/intrinsic/detail/segmented_begin.hpp:16:0,
from /opt/local/include/boost/fusion/sequence/intrinsic/begin.hpp:17, from
/opt/local/include/boost/fusion/iterator/segmented_iterator.hpp:12, from
/opt/local/include/boost/fusion/sequence/intrinsic/detail/segmented_end.hpp:11, from
/opt/local/include/boost/fusion/sequence/intrinsic/end.hpp:17, from
/opt/local/include/boost/fusion/sequence/intrinsic/back.hpp:11, from
/opt/local/include/boost/fusion/sequence/intrinsic.hpp:11, from
/opt/local/include/boost/fusion/include/intrinsic.hpp:10, from
/opt/local/include/boost/proto/fusion.hpp:22, from
/opt/local/include/boost/proto/core.hpp:21, from
/opt/local/include/boost/proto/proto.hpp:12, from
/opt/local/include/boost/spirit/home/support/meta_compiler.hpp:19, from
/opt/local/include/boost/spirit/home/qi/meta_compiler.hpp:14, from
/opt/local/include/boost/spirit/home/qi/action/action.hpp:14, from
/opt/local/include/boost/spirit/home/qi/action.hpp:14, from
/opt/local/include/boost/spirit/home/qi.hpp:14, from
/opt/local/include/boost/spirit/include/qi.hpp:16, from test_qi.cpp:1:
/opt/local/include/boost/fusion/container/list/cons.hpp: In instantiation of
'boost::fusion::cons<Car, Cdr>::cons(const boost::fusion::cons<Car2, Cdr2>&) [with Car2 =
int*&; Cdr2 = boost::fusion::nil; Car = int_holder&; Cdr = boost::fusion::nil]':
/opt/local/include/boost/spirit/home/support/context.hpp:117:20: required from
'boost::spirit::context<Attributes, Locals>::context(typename Attributes::car_type, const
Args&, Context&) [with Args =
boost::fusion::vector<boost::phoenix::actor<boost::spirit::attribute<0> >,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_,
boost::fusion::void_>; Context = boost::spirit::context<boost::fusion::cons<int*&,
boost::fusion::cons<int_holder&, boost::fusion::nil> >, boost::fusion::vector0<> >;
Attributes = boost::fusion::cons<int*&, boost::fusion::cons<int_holder&,
boost::fusion::nil> >; Locals = boost::fusion::vector0<>; typename Attributes::car_type =
int*&]' /opt/local/include/boost/spirit/home/qi/nonterminal/rule.hpp:343:67: required
from 'bool boost::spirit::qi::rule<Iterator, T1, T2, T3, T4>::parse(Iterator&, const
Iterator&, Context&, const Skipper&, Attribute&, const Params&) const [with Context =
boost::spirit::context<boost::fusion::cons<int*&, boost::fusion::cons<int_holder&,
boost::fusion::nil> >, boost::fusion::vector0<> >; Skipper = boost::spirit::unused_type;
Attribute = int*; Params =
boost::fusion::vector<boost::phoenix::actor<boost::spirit::attribute<0> >,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_,
boost::fusion::void_>; Iterator = const char*; T1 = int*(int_holder&); T2 =
boost::spirit::unused_type; T3 = boost::spirit::unused_type; T4 =
boost::spirit::unused_type]'
/opt/local/include/boost/spirit/home/qi/nonterminal/detail/parameterized.hpp:48:79:
required from 'bool boost::spirit::qi::parameterized_nonterminal<Subject,
Params>::parse(Iterator&, const Iterator&, Context&, const Skipper&, Attribute&) const
[with Iterator = const char*; Context = boost::spirit::context<boost::fusion::cons<int*&,
boost::fusion::cons<int_holder&, boost::fusion::nil> >, boost::fusion::vector0<> >;
Skipper = boost::spirit::unused_type; Attribute = int*; Subject =
boost::spirit::qi::rule<const char*, int*(int_holder&), boost::spirit::unused_type,
boost::spirit::unused_type, boost::spirit::unused_type>; Params =
boost::fusion::vector<boost::phoenix::actor<boost::spirit::attribute<0> >,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_,
boost::fusion::void_>]' /opt/local/include/boost/spirit/home/qi/action/action.hpp:65:13:
required from 'bool boost::spirit::qi::action<Subject, Action>::parse(Iterator&, const
Iterator&, Context&, const Skipper&, Attribute&) const [with Iterator = const char*;
Context = boost::spirit::context<boost::fusion::cons<int*&,
boost::fusion::cons<int_holder&, boost::fusion::nil> >, boost::fusion::vector0<> >;
Skipper = boost::spirit::unused_type; Attribute = boost::spirit::unused_type; Subject =
boost::spirit::qi::parameterized_nonterminal<boost::spirit::qi::rule<const char*,
int*(int_holder&), boost::spirit::unused_type, boost::spirit::unused_type,
boost::spirit::unused_type>,
boost::fusion::vector<boost::phoenix::actor<boost::spirit::attribute<0> >,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_,
boost::fusion::void_> >; Action =
boost::phoenix::actor<boost::phoenix::composite<boost::phoenix::assign_eval,
boost::fusion::vector<boost::spirit::attribute<0>, boost::spirit::argument<0>,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_> >
>]' /opt/local/include/boost/spirit/home/qi/detail/fail_function.hpp:38:72: required from
'bool boost::spirit::qi::detail::fail_function<Iterator, Context,
Skipper>::operator()(const Component&, Attribute&) const [with Component =
boost::spirit::qi::action<boost::spirit::qi::parameterized_nonterminal<boost::spirit::qi::rule<const
char*, int*(int_holder&), boost::spirit::unused_type, boost::spirit::unused_type,
boost::spirit::unused_type>,
boost::fusion::vector<boost::phoenix::actor<boost::spirit::attribute<0> >,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_,
boost::fusion::void_> >,
boost::phoenix::actor<boost::phoenix::composite<boost::phoenix::assign_eval,
boost::fusion::vector<boost::spirit::attribute<0>, boost::spirit::argument<0>,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_> >
> >; Attribute = boost::spirit::unused_type; Iterator = const char*; Context =
boost::spirit::context<boost::fusion::cons<int*&, boost::fusion::cons<int_holder&,
boost::fusion::nil> >, boost::fusion::vector0<> >; Skipper = boost::spirit::unused_type]'
/opt/local/include/boost/spirit/home/qi/detail/pass_container.hpp:263:38: [ skipping 10
instantiation contexts ] /opt/local/include/boost/function/function_template.hpp:1042:16:
required from 'boost::function<R(T0, T1, T2, T3)>::function(Functor, typename
boost::enable_if_c<boost::type_traits::ice_not<boost::is_integral<Functor>::value>::value,
int>::type) [with Functor =
boost::spirit::qi::detail::parser_binder<boost::spirit::qi::plus<boost::spirit::qi::action<boost::spirit::qi::parameterized_nonterminal<boost::spirit::qi::rule<const
char*, int*(int_holder&), boost::spirit::unused_type, boost::spirit::unused_type,
boost::spirit::unused_type>,
boost::fusion::vector<boost::phoenix::actor<boost::spirit::attribute<0> >,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_,
boost::fusion::void_> >,
boost::phoenix::actor<boost::phoenix::composite<boost::phoenix::assign_eval,
boost::fusion::vector<boost::spirit::attribute<0>, boost::spirit::argument<0>,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_> >
> > >, mpl_::bool_<false> >; R = bool; T0 = const char*&; T1 = const char* const&; T2 =
boost::spirit::context<boost::fusion::cons<int*&, boost::fusion::cons<int_holder&,
boost::fusion::nil> >, boost::fusion::vector0<> >&; T3 = const
boost::spirit::unused_type&; typename
boost::enable_if_c<boost::type_traits::ice_not<boost::is_integral<Functor>::value>::value,
int>::type = int]' /opt/local/include/boost/function/function_template.hpp:1083:5:
required from 'typename
boost::enable_if_c<boost::type_traits::ice_not<boost::is_integral<Functor>::value>::value,
boost::function<R(T0, T1, T2, T3)>&>::type boost::function<R(T0, T1, T2,
T3)>::operator=(Functor) [with Functor =
boost::spirit::qi::detail::parser_binder<boost::spirit::qi::plus<boost::spirit::qi::action<boost::spirit::qi::parameterized_nonterminal<boost::spirit::qi::rule<const
char*, int*(int_holder&), boost::spirit::unused_type, boost::spirit::unused_type,
boost::spirit::unused_type>,
boost::fusion::vector<boost::phoenix::actor<boost::spirit::attribute<0> >,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_,
boost::fusion::void_> >,
boost::phoenix::actor<boost::phoenix::composite<boost::phoenix::assign_eval,
boost::fusion::vector<boost::spirit::attribute<0>, boost::spirit::argument<0>,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_> >
> > >, mpl_::bool_<false> >; R = bool; T0 = const char*&; T1 = const char* const&; T2 =
boost::spirit::context<boost::fusion::cons<int*&, boost::fusion::cons<int_holder&,
boost::fusion::nil> >, boost::fusion::vector0<> >&; T3 = const
boost::spirit::unused_type&; typename
boost::enable_if_c<boost::type_traits::ice_not<boost::is_integral<Functor>::value>::value,
boost::function<R(T0, T1, T2, T3)>&>::type = boost::function<bool(const char*&, const
char* const&, boost::spirit::context<boost::fusion::cons<int*&,
boost::fusion::cons<int_holder&, boost::fusion::nil> >, boost::fusion::vector0<> >&,
const boost::spirit::unused_type&)>&]'
/opt/local/include/boost/spirit/home/qi/nonterminal/rule.hpp:182:13: required from
'static void boost::spirit::qi::rule<Iterator, T1, T2, T3,
T4>::define(boost::spirit::qi::rule<Iterator, T1, T2, T3, T4>&, const Expr&, mpl_::true_)
[with Auto = mpl_::bool_<false>; Expr =
boost::proto::exprns_::expr<boost::proto::tagns_::tag::unary_plus,
boost::proto::argsns_::list1<const
boost::proto::exprns_::expr<boost::proto::tagns_::tag::subscript,
boost::proto::argsns_::list2<boost::proto::exprns_::expr<boost::proto::tagns_::tag::terminal,
boost::proto::argsns_::term<boost::spirit::qi::parameterized_nonterminal<boost::spirit::qi::rule<const
char*, int*(int_holder&), boost::spirit::unused_type, boost::spirit::unused_type,
boost::spirit::unused_type>,
boost::fusion::vector<boost::phoenix::actor<boost::spirit::attribute<0> >,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_,
boost::fusion::void_> > >, 0l>&,
boost::proto::exprns_::expr<boost::proto::tagns_::tag::terminal,
boost::proto::argsns_::term<const
boost::phoenix::actor<boost::phoenix::composite<boost::phoenix::assign_eval,
boost::fusion::vector<boost::spirit::attribute<0>, boost::spirit::argument<0>,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_> >
>&>, 0l> >, 2l>&>, 1l>; Iterator = const char*; T1 = int*(int_holder&); T2 =
boost::spirit::unused_type; T3 = boost::spirit::unused_type; T4 =
boost::spirit::unused_type; boost::spirit::qi::rule<Iterator, T1, T2, T3, T4> =
boost::spirit::qi::rule<const char*, int*(int_holder&), boost::spirit::unused_type,
boost::spirit::unused_type, boost::spirit::unused_type>; mpl_::true_ =
mpl_::bool_<true>]' /opt/local/include/boost/spirit/home/qi/nonterminal/rule.hpp:220:13:
required from 'boost::spirit::qi::rule<Iterator, T1, T2, T3, T4>&
boost::spirit::qi::rule<Iterator, T1, T2, T3, T4>::operator=(const Expr&) [with Expr =
boost::proto::exprns_::expr<boost::proto::tagns_::tag::unary_plus,
boost::proto::argsns_::list1<const
boost::proto::exprns_::expr<boost::proto::tagns_::tag::subscript,
boost::proto::argsns_::list2<boost::proto::exprns_::expr<boost::proto::tagns_::tag::terminal,
boost::proto::argsns_::term<boost::spirit::qi::parameterized_nonterminal<boost::spirit::qi::rule<const
char*, int*(int_holder&), boost::spirit::unused_type, boost::spirit::unused_type,
boost::spirit::unused_type>,
boost::fusion::vector<boost::phoenix::actor<boost::spirit::attribute<0> >,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_,
boost::fusion::void_> > >, 0l>&,
boost::proto::exprns_::expr<boost::proto::tagns_::tag::terminal,
boost::proto::argsns_::term<const
boost::phoenix::actor<boost::phoenix::composite<boost::phoenix::assign_eval,
boost::fusion::vector<boost::spirit::attribute<0>, boost::spirit::argument<0>,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_,
boost::fusion::void_, boost::fusion::void_, boost::fusion::void_, boost::fusion::void_> >
>&>, 0l> >, 2l>&>, 1l>; Iterator = const char*; T1 = int*(int_holder&); T2 =
boost::spirit::unused_type; T3 = boost::spirit::unused_type; T4 =
boost::spirit::unused_type; boost::spirit::qi::rule<Iterator, T1, T2, T3, T4> =
boost::spirit::qi::rule<const char*, int*(int_holder&), boost::spirit::unused_type,
boost::spirit::unused_type, boost::spirit::unused_type>]' test_qi.cpp:41:3: required from
'my_grammar<Iterator>::my_grammar() [with Iterator = const char*]' test_qi.cpp:57:26:
required from here /opt/local/include/boost/fusion/container/list/cons.hpp:83:40: error:
invalid initialization of reference of type 'boost::fusion::cons<int_holder&,
boost::fusion::nil>::car_type {aka int_holder&}' from expression of type 'int*'
C'è ovviamente un problema quando si passa alla funzione _r1 la fenice ::, ma non ho idea di come risolvilo. Grazie in anticipo.
per favore inserisci la tua ricerca come risposta alla tua domanda nella casella di testo qui sotto, piuttosto che fare un aggiornamento. Questo per rendere più facile per i googler trovare questa risposta. Oppure vota per chiudere questa domanda. – vidstige
@vidstige Hai ragione! Fatto, grazie – Giuliano