boost :: program_options: Parameter mit einem festen und einem variablen Token?

8

Ist es möglich, Parameter dieser Art mit boost :: program_options zu verwenden?

%Vor%

, d. h., ist es möglich, den Parameternamen mit einem ersten Token (z. B. -p ) gefolgt von einer Zahl dynamisch zu spezifizieren? Ich möchte das vermeiden:

%Vor%     
Pietro 21.03.2013, 18:01
quelle

1 Antwort

11

Boost.ProgramOptions bietet keine direkte Unterstützung dafür. Dennoch gibt es zwei allgemeine Lösungen, die jeweils ihre Kompromisse haben:

  • Platzhalteroptionen.
  • Benutzerdefinierter Parser.

Platzhalteroptionen

Wenn es akzeptabel ist, --p anstelle von -p zu verwenden, kann eine Wildcard-Option verwendet werden. Dazu muss während der Extraktion durch variables_map iteriert werden, da Boost.ProgramOptions keine Unterstützung bietet, wenn sowohl der Schlüssel als auch der Wert in einer überladenen validate() -Funktion empfangen wird.

%Vor%

Und seine Verwendung:

%Vor%

Bei diesem Ansatz muss über die gesamte Map iteriert werden, um Übereinstimmungen mit Platzhaltern zu identifizieren, was zu einer Komplexität von O(n) führt. Außerdem muss die gewünschte Syntax geändert werden, wobei --p1 123 anstelle von -p1 123 verwendet werden muss. Diese Einschränkung ist das Ergebnis des Standard-Parser-Verhaltens von Boost.ProgramOptions, bei dem erwartet wird, dass ein einzelner Bindestrich von einem einzelnen Zeichen gefolgt wird.

Benutzerparser

Der alternative Ansatz besteht darin, einen benutzerdefinierten Parser hinzuzufügen an die command_line_parser . Ein benutzerdefinierter Parser erlaubt die -p1 -Syntax sowie andere gängige Formulare wie --p1 123 und -p1=123 . Es gibt ein paar Verhaltensweisen, die behandelt werden müssen:

  • Ein Parser erhält jeweils ein einzelnes Token. Daher wird es bei einzelnen Aufrufen p1 und 123 erhalten. Es ist die Aufgabe des Parsers, p1 mit 123 zu verbinden.
  • Boost.ProgramOptions erwartet, dass mindestens ein Parser ein Token behandelt. Andernfalls wird boost::program_options::unknown_option ausgegeben.

Um diese Verhaltensweisen zu berücksichtigen, verwaltet der benutzerdefinierte Parser den Status und führt die Kodierung / Dekodierung durch:

  • Wenn der Parser p1 empfängt, extrahiert er 1 und speichert den Status im Parser. Darüber hinaus codiert es einen Wert no operation für p .
  • Wenn der Parser 123 empfängt, codiert er ihn neben dem gespeicherten Status als Wert für p .

Wenn also der Parser -p1 und 123 empfängt, werden 2 Werte in den variables_map für p eingefügt: der Wert no operation und 1:123 .

%Vor%

Diese Codierung kann für den Benutzer transparent sein, indem eine Hilfsfunktion bereitgestellt wird, um den codierten p -Vektor in eine Karte zu transformieren. Das Ergebnis der Decodierung wäre:

%Vor%

Hier ist der Beispielcode:

%Vor%

Und seine Verwendung:

%Vor%

Abgesehen davon, dass es sich um eine größere Lösung handelt, ist ein Nachteil die Anforderung, den Decodierungsprozess zu durchlaufen, um die gewünschten Werte zu erhalten. Man kann nicht einfach die Ergebnisse von vm["p"] auf sinnvolle Weise iterieren.

    
Tanner Sansbury 05.04.2013, 14:40
quelle