2014-05-14 14 views
5

Con le opzioni della riga di comando, posso effettuare le seguenti operazioni:Analisi delle opzioni non registrate per i file di configurazione in Boost program_options?

po::variables_map vm; 
auto parsedOptions = po::command_line_parser(argc, argv).options(optionsDescription1).allow_unregistered().run(); 
po::store(parsedOptions, vm); 
po::notify(vm); 

auto unregistered = po::collect_unrecognized(parsedOptions.options, po::include_positional); 
po::variables_map vm2; 
auto parsedOptions2 = po::command_line_parser(unregistered).options(optionsDescription2).run(); 
po::store(parsedOptions2, vm2); 
po::notify(vm2); 

Questo funziona bene, perché collect_unregistered() raccoglie la linea di comando pedine esattamente come appariva nella riga di comando. Tuttavia, non funziona per i file di configurazione. Posso analizzare un file di configurazione che consente opzioni non registrate, ma quando raccolgo le opzioni non registrate, ottengo un risultato che non posso utilizzare.

po::variables_map vm; 
auto parsedOptions = po::parse_config_file<char>(filename, optionsDescription1, true); 
po::store(parsedOptions, vm); 
po::notify(vm); 
auto unregistered = po::collect_unrecognized(parsedOptions.options, po::include_positional); 

In questo caso ottengo i nomi e i valori delle opzioni elencate. Ad esempio, se il file di configurazione contiene le seguenti opzioni:

unregistered_option1=value1 
unregistered_option2=value2 

tanto sono i valori unregistered_option1, value1, unregistered_option2, value2 nel vettore stringa di unregistered. Il parser di Boost non può fare nulla di utile con questo formato. C'è un modo per analizzare questo elenco (ad esempio, analizzare tutte le opzioni che non erano state riconosciute dal primo options_description con un diverso options_description)? Naturalmente posso solo analizzare il file di nuovo con il secondo options_description con il set allow_unregistered, ma non riesco a verificare le opzioni sconosciute per entrambe le descrizioni.

risposta

3

Non dovete fare affidamento sulle imperfezioni del valore collect_unrecognized() di ritorno, si può sempre individuare, gestire e ricostruire le opzioni da soli, come il risultato di parse_config_file() mantiene la relazione osservata per le opzioni sconosciuti:

auto parsed_options = parse_config_file(ifs, config_file_options, true); 
store(parsed_options, vm); 
... 
for (const auto& o : parsed_options.options) { 
    if (vm.find(o.string_key) == vm.end()) { 
     // an unknown option 
     cout << o.string_key << "=" << o.value << "\n"; 
    } 
} 
+0

Non so da quando, ma ora c'è un membro di dati bool ".unregistered" nelle singole opzioni che sono in loop. Quindi non c'è bisogno di cercare tutti i 'vm' per scoprire se non è stato registrato più. – PeterT