继承时删除重复的模板类型名条目

Remove duplicate template typename entry when inheriting

我有一个模板 class 我继承自(从现在起引用为 parent)。

模板 class 初始化一个包含 classes 和 child class.

中指定的构造函数的融合列表成员变量
template<typename... ITEM_TYPES>
using List = boost::fusion::list<ITEM_TYPES...>;

template<typename... CHILDREN_TYPES>
class ElementContainer 
{ 
protected:
    const List<CHILDREN_TYPES...> children;
public:
     ElementContainer(CHILDREN_TYPES&&... args) : children(forward<CHILDREN_TYPES>(args)...) {}
};

childclass的例子:

class XMLSignatureDocument : public ElementContainer<XMLDeclarationElement, SignatureXMLElement>
{
public:
    XMLSignatureDocument() :ElementContainer(
        XMLDeclarationElement("<?xml version=\"1.0\" encoding=\"utf-8\"?>"),
        SignatureXMLElement("<Signature xmlns=\"http://www.w3.org/2000/09/xmldsig#\"></signature>"
        )) {};
};

当我创建这样一个 child class 时,我必须在列表中指定两次 classes 的类型:

一旦在 "inherit from" 规范中:

class XMLSignatureDocument : public ElementContainer<XMLDeclarationElement, SignatureXMLElement>

以及当我指定单个 classes 的构造函数参数时:

XMLSignatureDocument() :ElementContainer(
    XMLDeclarationElement("<?xml version=\"1.0\" encoding=\"utf-8\"?>"),
    SignatureXMLElement("<Signature xmlns=\"http://www.w3.org/2000/09/xmldsig#\"></signature>"
    )) {};

我想只指定一次 - 当我还指定构造函数参数时,如下所示:

class XMLSignatureDocument : public ElementContainer<...>
{
public:
    XMLSignatureDocument() :ElementContainer(
        XMLDeclarationElement("<?xml version=\"1.0\" encoding=\"utf-8\"?>"),
        SignatureXMLElement("<Signature xmlns=\"http://www.w3.org/2000/09/xmldsig#\"></signature>"
        )) {};
};

并且在 parent class.

中仍然有列表的编译时创建

如果不可能,我不会 100% 锁定在这个设计中 - 如果可以用另一种设计实现同样的效果,我想听听。

我正在使用 Visual Studio 2014 (v140)(c++14) 编译工具集和 boost 库。

您可以做相反的事情:在 class 声明中指定类型,并对构造函数参数使用通用初始化语法(尽管它不适用于显式构造函数):

class XMLSignatureDocument : public ElementContainer<XMLDeclarationElement, SignatureXMLElement>
{
public:
    XMLSignatureDocument() :ElementContainer(
        {"<?xml version=\"1.0\" encoding=\"utf-8\"?>"},
        {"<Signature xmlns=\"http://www.w3.org/2000/09/xmldsig#\"></signature>"}
        ) {};
};

您可以在 ElementContainer 构造函数中构造模板参数类型。这将适用于 explicit 构造函数,但前提是它们采用单个参数。

ElementContainer 构造函数更改为将参数转发给 CHILDREN_TYPES 构造函数的模板函数:

template <typename... Args>
ElementContainer(Args&&... args) 
    : children(CHILDREN_TYPES{std::forward<Args>(args)}...) {}

然后你可以自己传递字符串:

XMLSignatureDocument() :ElementContainer(
        "<?xml version=\"1.0\" encoding=\"utf-8\"?>",
        "<Signature xmlns=\"http://www.w3.org/2000/09/xmldsig#\"></signature>") {};