Domanda

Ho questo semplice parser lo scopo di analizzare stile VB corde doppie virgolette. Così, il parser dovrebbe girare qualcosa come

"This is a quoted string containing quotes ("" "")"

in una potenza di

This is a quoted string containing quotes (" ")

Questa è la grammatica sono arrivato fino a questo:

namespace qi = boost::spirit::qi;
namespace wide = qi::standard_wide;
class ConfigurationParser : public qi::grammar<std::wstring::iterator, std::wstring()>
{
    qi::rule<std::wstring::iterator, std::wstring()> quotedString;
    qi::rule<std::wstring::iterator> doubleQuote;

public:
    ConfigurationParser() : ConfigurationParser::base_type(quotedString, "vFind Command Line")
    {
        doubleQuote = (wide::char_(L'"') >> wide::char_(L'"'));

        quotedString = L'"' >> +(doubleQuote[qi::_val = L'"'] | (wide::char_ - L'"'))>> L'"';
    }
};

Tuttavia, l'attributo sto ottenendo è un marchio singolo apice ( "), piuttosto che il messaggio analizzata completo.

È stato utile?

Soluzione

È possibile farlo senza azioni semantiche:

class ConfigurationParser 
  : public qi::grammar<std::wstring::iterator, std::wstring()> 
{ 
    qi::rule<std::wstring::iterator, std::wstring()> quotedString; 
    qi::rule<std::wstring::iterator, wchar_t()> doubleQuote; 

public: 
    ConfigurationParser() 
      : ConfigurationParser::base_type(quotedString, "vFind Command Line") 
    { 
        doubleQuote = wide::char_(L'"') >> omit[wide::char_(L'"')]; 
        quotedString = L'"' >> +(doubleQuote | (wide::char_ - L'"')) >> L'"'; 
    } 
}; 

La direttiva omit[] esegue ancora il parser incorporato, ma non espone qualsiasi attributo, rendendo la regola doubleQuote restituire un singolo L'"'.

Altri suggerimenti

Credo che non lo fai salvare il risultato corretto:

doubleQuote[qi::_val = L'"']

Qui, a causa del segno '=', si ignora ciò che era già in. Provate con '+ =' invece.

doubleQuote[qi::_val += L'"']

Inoltre, non so se il risparmio è automatico, potrebbe essere necessario aggiungere lo stesso '+ =' dopo l'altro parser in subordine:

(wide::char_ - L'"')[qi::_val += boost::spirit::arg_names::_1]

Ma io non sono che il bene con Qi quindi forse è automatizzato, che avrebbe senso.

Beh, io non sono del tutto sicuro perché, ma sono stato in grado di risolvere il problema spostando l'azione assegnazione in regola sotto:

doubleQuote %= (wide::char_(L'"') >> L'"')[qi::_val = L'"'];
doubleQuote.name("double quote");

quotedString = L'"' >> +(doubleQuote | (wide::char_ - L'"')) >> L'"';
quotedString.name("quoted string");

Si noti l'uso di operator %= per doubleQuote e il fatto che l'azione semantica si trova ora là.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top