C++11 初始值设定项列表作为可变模板参数

C++11 初始值设定项列表作为可变模板参数,c++11,variadic-templates,C++11,Variadic Templates,我有两个类a、B和F,它们都有不同的构造函数签名,如下所示: class A { public: A() {} }; class B { double x_, y_; public: B(double x, double y) : x_(x), y_(y) {} }; class F { vector<unsigned> factors_; public: F(std::initializer_list<unsigned> f

我有两个类a、B和F,它们都有不同的构造函数签名,如下所示:

class A {
public:
     A() {}
};

class B {
    double x_, y_;
public:
    B(double x, double y) : x_(x), y_(y) {}
};

class F {
    vector<unsigned> factors_;
public:
    F(std::initializer_list<unsigned> factors) : factors_(factors) {}
};
A类{
公众:
A(){}
};
B类{
双x,y;
公众:
B(双x,双y):x(x),y(y){}
};
F类{
矢量因子;
公众:
F(std::initializer_list factors):factors_u(factors){
};
这些类的对象需要在某处注册,因此构造应该经过工厂,如下所示:

template<class R, typename... Args>
inline R & factory(Args &&... args)
{
    R * rp = new R(std::forward<Args>(args)...);
    /* do fancy stuff with rp... */
    return *rp;
}
模板
内联R&factory(参数和…参数)
{
R*rp=新的R(标准:正向(参数)…);
/*用rp做些花哨的事*/
返回*rp;
}
这适用于类A和B,但不适用于F,因为typename。。。要采用一种或多种类型:

A & a = factory<A>();   // okay     
B & b = factory<B>(0.707107, 0.707107);  // okay
F & f = factory<F>({2, 3, 5, 7, 11});  // error: no matching function for call to ‘F::F()’ in factory
A&A=factory();//可以
食宿=工厂(0.707107,0.707107);//可以
F&F=工厂({2,3,5,7,11});//错误:工厂中没有与调用“F::F()”匹配的函数
问题:是否有任何方法可以使其与常规
工厂(args…
语法一起工作

我尝试了对
的工厂函数进行完全专门化,但要么把语法搞砸了,要么在编译时编译器没有将其作为工厂


还有其他想法吗?

回答这个问题:我看不到一种简单的方法可以重用需要初始值设定项列表的factory方法

我个人会在F类中添加一个构造函数,使用
std::vector

F(const std::vector<unsigned>& factors) : factors_(factors) {}

如果只想用一些值填充F类向量,则不需要工厂

这可能不是您首选的语法,但您可以强制工厂方法传递初始值设定项列表:

F & f = factory<F>(std::initializer_list<unsigned>{2u, 3u, 5u, 7u, 11u});

我很惊讶变量模板不能更好地处理初始化列表。

OP在初始化过程中使用了整数。这将破坏std::initializer\u list args,因为…list不能转换为…list。@Werner是的,这就是我显式使用无符号int的原因。是的,但他没有,您在回答中没有对此进行澄清。除此之外,我同意你的答案(尽管我认为使用vector是一个更好的选择),我也开始类似于你。在更完整的代码中,你可以想象工厂是在某处注册对象的。
F f2{2, 3, 5, 7, 11};
F & f = factory<F>(std::initializer_list<unsigned>{2u, 3u, 5u, 7u, 11u});
template<class R>
inline R& do_fancy_stuff_with(R *r)
{
    /* do fancy stuff here... */
    return *r;
}

template<class R, typename... Args>
inline R & factory(Args &&... args)
{
    R * rp = new R(std::forward<Args>(args)...);
    return do_fancy_stuff_with(rp);
}

template<class R, typename T>
inline R & factory(std::initializer_list<T> args)
{
    R * rp = new R(std::move(args));
    return do_fancy_stuff_with(rp);
}

A & a = factory<A>();
B & b = factory<B>(0.707107, 0.707107);
F & f = factory<F>({2u, 3u, 5u, 7u, 11u});