Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Insert into boost::program_options::variables_map by index operator

Tags:

I have a boost::program_options::variables_map args. Now I want to insert into this map manually like a key-value pair. Example:

boost::program_options::variables_map args

args["document"] = "A";

args["flag"] = true;

The problem is that I already have these 2 options

desc.add_options()
    ("document", po::value<std::string>())
    ("flag", po::value<bool>());

but they are given empty input from the command line sometimes. So if they are empty, then I have to update them inside the po::variables_map args itself

like image 569
etotientz Avatar asked May 09 '19 09:05

etotientz


2 Answers

The library is designed to store the arguments after parsing from command line, or from a file. You cannot directly use the operator[] to assign values like a std::map because it returns a const reference, see the annotation here:

const variable_value & operator[](const std::string &) const;

If you really really want to assign manually the key values, you could create a std::stringstream and parse it with the library, see the following example program

#include <string>
#include <sstream>
#include <iostream>
#include <boost/program_options/options_description.hpp>
#include <boost/program_options/parsers.hpp>
#include <boost/program_options/variables_map.hpp>

int main()
{
  namespace po = boost::program_options;

  std::stringstream s;
  s << "document=A" << std::endl << "flag=true" << std::endl;

  po::options_description desc("");
  desc.add_options()
    ("document", po::value<std::string>())
    ("flag", po::value<bool>());

  po::variables_map vm;
  po::store(po::parse_config_file(s, desc, true), vm);
  po::notify(vm);

  std::cout << "document is: " << vm["document"].as<std::string>() << std::endl;
  std::cout << "flag is: " << (vm["flag"].as<bool>() ? "true" : "false") << std::endl;

  return 0;
}

If you instead just want to insert a value for some keys when they are absent, you can just use the default_value options as described in the documentation of boost::program_options.

For example:

  po::options_description desc("");
  desc.add_options()
    ("document", po::value<std::string>()->default_value("default_document")
    ("flag", po::value<bool>()->default_value(false));
like image 132
francesco Avatar answered Nov 15 '22 06:11

francesco


Since it publicly inherits from std::map<std::string, variable_value> it should be relatively safe to cast it to std::map and use as such:

(*static_cast<std::map<std::string, variable_value>*>(my_variable_map))[name] = value;

There's no guarantee that this is enough to make variable_map use it, but currently it seems to be: cpp, h.

It's annoying that this is needed.

like image 34
himself Avatar answered Nov 15 '22 04:11

himself