00001
00015 #ifndef _DLRUTILITIES_OPTIONPARSER_H_
00016 #define _DLRUTILITIES_OPTIONPARSER_H_
00017
00018 #include <map>
00019 #include <string>
00020 #include <vector>
00021 #include <dlrUtilities/optionDescription.h>
00022 #include <dlrUtilities/stringManipulation.h>
00023
00024 namespace dlr {
00025
00026 namespace utilities {
00027
00028
00125 class OptionParser {
00126 public:
00127
00167 OptionParser(bool allowExtraArguments = true,
00168 bool allowStackedShortOptions = true,
00169 bool allowOptionishArguments = false);
00170
00171
00202 explicit
00203 OptionParser(int exitCode,
00204 bool handleMinusMinusHelp = true,
00205 bool printUsage = true,
00206 bool allowExtraArguments = true,
00207 bool allowStackedShortOptions = true,
00208 bool allowOptionishArguments = false);
00209
00210
00214 ~OptionParser();
00215
00216
00245 void
00246 addOption(const std::string& name,
00247 const std::string& shortVersion,
00248 const std::string& longVersion,
00249 const std::string& docString,
00250 bool allowPartialMatch = true);
00251
00252
00292 void
00293 addOptionWithValue(const std::string& name,
00294 const std::string& shortVersion,
00295 const std::string& longVersion,
00296 const std::string& defaultValue,
00297 const std::string& docString,
00298 bool requireArgument = true,
00299 bool allowPartialMatch = true,
00300 bool allowOptionishValue = false);
00301
00302
00340 void
00341 addPositionalArgument(const std::string& name,
00342 const std::string& docString,
00343 bool isRequired = false,
00344 const std::string& defaultValue = "");
00345
00346
00368 template<class Type>
00369 Type
00370 convertValue(const std::string& name);
00371
00372
00394 template<class Type>
00395 Type
00396 convertValue(const std::string& name, int valueIndex);
00397
00398
00414 size_t
00415 getCount(const std::string& name) const;
00416
00417
00430 std::vector<std::string>
00431 getExtraPositionalArguments();
00432
00433
00449 std::string
00450 getOptionsDescription();
00451
00452
00466 std::string
00467 getUsage();
00468
00469
00491 std::string
00492 getValue(const std::string& name);
00493
00494
00517 std::string
00518 getValue(const std::string& name, int valueIndex);
00519
00520
00532 template<class Type>
00533 Type
00534 getValue(const std::string& name, type_tag<Type>);
00535
00536
00551 template<class Type>
00552 Type
00553 getValue(const std::string& name, int valueIndex, type_tag<Type>);
00554
00555
00579 void
00580 parseCommandLine(int argc, const char* argv[]);
00581
00582
00594 void
00595 parseCommandLine(int argc, char* argv[]);
00596
00597
00598 private:
00599
00600
00601 enum ErrorBehavior {ExitOnError, ThrowOnError, UsageAndExitOnError};
00602
00603
00604
00605 bool
00606 findOptionDescription(const std::string& argument,
00607 OptionDescription& optionDescription,
00608 size_t& typedLength,
00609 bool& isShortMatch);
00610
00611
00612 void
00613 recordPositionalArgument(const std::string& argument);
00614
00615
00616
00617 bool m_allowExtraArguments;
00618 bool m_allowOptionishArguments;
00619 bool m_allowStackedShortOptions;
00620 ErrorBehavior m_errorBehavior;
00621 int m_exitCode;
00622 std::vector<std::string> m_extraArgumentValues;
00623 bool m_handleHelp;
00624 size_t m_numberOfPosArgRequired;
00625 size_t m_numberOfPosArgParsed;
00626 std::map<std::string, size_t> m_optionCounts;
00627 std::map<std::string, OptionDescription> m_optionDescriptions;
00628 std::map< std::string, std::vector<std::string> > m_optionValues;
00629 std::vector<std::string> m_positionalArgumentNames;
00630 std::vector<std::string> m_positionalArgumentDefaultValues;
00631 std::vector<std::string> m_positionalArgumentDocs;
00632 std::string m_programName;
00633
00634 };
00635
00636 }
00637
00638 }
00639
00640
00641
00642 namespace dlr {
00643
00644 namespace utilities {
00645
00646
00647 template<class Type>
00648 Type
00649 OptionParser::
00650 convertValue(const std::string& name)
00651 {
00652 try {
00653 return convertString<Type>(this->getValue(name));
00654 } catch(ConversionException&) {
00655 std::ostringstream message;
00656 message << "Error when parsing option " << name << ": "
00657 << "can't convert \"" << this->getValue(name)
00658 << "\" to appropriate type.";
00659 DLR_THROW(ConversionException, "OptionParser::convertValue()",
00660 message.str().c_str());
00661 }
00662 }
00663
00664
00665 template<class Type>
00666 Type
00667 OptionParser::
00668 convertValue(const std::string& name, int valueIndex)
00669 {
00670 try {
00671 return convertString<Type>(this->getValue(name, valueIndex));
00672 } catch(ConversionException&) {
00673 std::ostringstream message;
00674 message << "Error when parsing option " << name << ": "
00675 << "can't convert \"" << this->getValue(name, valueIndex)
00676 << "\" to appropriate type.";
00677 DLR_THROW(ConversionException, "OptionParser::convertValue()",
00678 message.str().c_str());
00679 }
00680 }
00681
00682
00683 template<class Type>
00684 Type
00685 OptionParser::
00686 getValue(const std::string& name, type_tag<Type>)
00687 {
00688 return this->convertValue<Type>(name);
00689 }
00690
00691
00692 template<class Type>
00693 Type
00694 OptionParser::
00695 getValue(const std::string& name, int valueIndex, type_tag<Type>)
00696 {
00697 return this->convertValue<Type>(name, valueIndex);
00698 }
00699
00700
00701 }
00702
00703 }
00704
00705 #endif // #ifndef _DLRUTILITES_OPTIONPARSER_H_