我现在开始使用boost :: program_options来解析命令行选项以及配置文件。
是否可以使用自己的模板类作为选项参数?这意味着,像
#include <iostream>
#include "boost/program_options.hpp"
namespace po = boost::program_options;
template <typename T>
class MyClass
{
private:
T* m_data;
size_t m_size;
public:
MyClass( size_t size) : m_size(size) { m_data = new T[size]; }
~MyClass() { delete[] m_data; }
T get( size_t i ) { return m_data[i]; }
void set( size_t i, T value ) { m_data[i] = value; }
};
int main (int argc, const char * argv[])
{
po::options_description generic("General options");
generic.add_options() ("myclass", po::value< MyClass<int>(2) >(),
"Read MyClass");
return 0;
}
尝试编译这个我得到一个语义问题(没有匹配函数来调用'value')。我想我需要为一般化类型提供一些演员,但我没有真正的想法。
有人可以帮忙吗? 感谢
Aeon512
答案 0 :(得分:2)
我不知道boost :: program_options是否允许你正在尝试的用例,但是你得到的错误是因为你试图将一个对象作为模板类型传递给po :: value&lt;&gt;。如果在编译时已知大小,则可以将大小作为模板参数传入。
template< typename T, size_t size >
class MyClass {
T m_data[size];
public:
// ...
};
然后像这样使用它:
po::value< MyClass<int, 2> >()
您还应该考虑使用Boost.Array而不是我想要实现您要实现的目标。
答案 1 :(得分:1)
我会这样写:
MyClass<int> mine(2);
generic.add_options() ("myclass", po::value(&mine), "Read MyClass");
然后,所有需要做的就是定义一个输入流运算符,如下所示:
std::istream& operator >>(std::istream& source, MyClass& target);
然后,当使用myclass
选项时,Boost Program Options将调用此流运算符,并且您的对象将根据该运算符的实现自动填充,而不必稍后调用其中一个程序选项函数来提取价值。
如果你不喜欢上面的语法,那么它也应该有用:
generic.add_options() ("myclass", po::value<MyClass<int> >()->default_value(MyClass<int>(2)), "Read MyClass");
这样,您将直接使用模板部分之外的所需构造函数参数创建类的实例,其中不允许运行时行为。我不喜欢这种方式,因为它很冗长,你最后需要调用更多函数来转换值。