| 12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485 |
- #pragma once
- #include <map>
- #include <string>
- #include <vector>
- namespace program {
- template <typename Impl>
- class Arguments {
- protected:
- struct Option;
- struct Positional;
- template <typename, typename> struct WithDefault;
- public:
- Arguments() = default;
- Arguments(int argc, char const * const * const argv);
- auto option(std::string const &name, std::string const &description = "");
- auto argument(size_t index, std::string const &name, std::string const &description = "");
- private:
- void usage() const;
- private:
- // Metadata variables
- bool primed_{false};
- std::map<std::string, std::string> option_descriptions;
- std::map<std::string, std::string> positional_descriptions;
- std::map<std::string, std::string> option_name_mapping;
- std::map<size_t, std::string> argument_names;
- // Data variables
- std::string program;
- size_t optional_from{std::numeric_limits<size_t>::max()};
- std::map<std::string, std::string> options;
- std::vector<std::string> arguments;
- };
- template <typename Impl>
- template <typename B, typename V>
- struct Arguments<Impl>::WithDefault {
- B impl;
- V default_value;
- template <typename T> operator T() const { return impl ?: T(default_value); }
- };
- template <typename Impl>
- struct Arguments<Impl>::Option {
- Arguments<Impl> *self;
- std::string name;
- char abbrev;
- std::string description;
- template <typename T> auto operator=(T &&value);
- template <typename T> operator T() const;
- bool primed() const;
- explicit operator bool() const;
- };
- template <typename Impl>
- struct Arguments<Impl>::Positional {
- Arguments<Impl> *self;
- size_t index;
- bool is_optional;
- std::string name;
- std::string description;
- template <typename T> auto operator=(T &&value);
- template <typename T> operator T() const;
- bool primed() const;
- explicit operator bool() const;
- };
- }
- #include "arguments_impl.hpp"
- #define TYPED_MAIN(tname) \
- int typed_main(tname const &args); \
- int main(int argc, char const * const * const argv) { \
- return typed_main(tname(argc, argv)); \
- } \
- int typed_main(tname const &args)
|