模板化类,如何在不使此类模板化的情况下表示为另一个类的成员变量

Templated classes, how to represent as a member variable of another class without making this class templated

本文关键字:表示 情况下 成员 变量 另一个      更新时间:2023-10-16

>我有一个模板化类,

template<typename T>
class TClass
{
public:
   //functions here
};
class Holding {
  public:
 private:
  TClass<T>  m_item;  //don't want this
};
int main() {
   Holding hd;
   //do whatever
   return 0;
}

我想要在 Holding 中创建一个实例变量,但不想让 Holding 成为模板类。 我的设计选项是什么?

看起来你想持有任何类型。如果确实如此,那么您可以使用boost::any

class Holding {
  public:
 private:
  TClass<boost::any>  m_item;  //you want this?
};

如果您不使用 Boost,那么您可以自己实现any或在此站点上搜索其实现或使用 google。

从非模板基类派生TClass B,并Holding持有指向B的指针(可能是std::unique_ptr)。

我可能没有正确理解你的问题。基本上,您有一个模板类 TClass,需要通过模板参数进行配置。然后,您拥有拥有TClass的Hold,但出于任何原因,您都不想将Holding作为模板。

这意味着 Holding 需要静态定义模板参数是什么

TClass<SomeClass> m_item;

现在,你在代码中说你不想要这个...我不确定您是不想提供模板参数还是提供 T。如果是 T,上面的代码将解决您的问题。否则,您需要使用 typedef 来删除模板参数并具有"无模板"类型,例如:

typedef TClass<int> intTClass; // replace int by whatever param you want

然后可以用作

class Holding {
  public:
 private:
  intTClass m_item;  //don't want this
};

如果可能的馆藏足够相似,则可以使用类型擦除。

#include <memory>
class HeldType {
public:
  virtual void myfunc() = 0;
  virtual ~HeldType() {}
};
template<typename T>
class HeldTypeModel : public HeldType {
public:
  HeldTypeModel(const T& t) : data_(t) {}
  void myfunc() { data_.myfunc(); }
private:
  T data_;
};
class TClass {
public:
  TClass() : x_(nullptr) {}
  template<typename T> 
  void set_t(const T& t) {
    x_.reset(new HeldTypeModel<T>(t));
  }
  std::unique_ptr<HeldType> x_;
};
class model {
public:
  void myfunc() {}
};
int main()
{
  TClass x;
  x.set_t(model{});
  return 0;
}

您需要弄清楚所有可能的 T 之间的共性是什么。您可能还想添加一些函数来获取typeid并抛弃实际类型等。看看boost::any.

如果你更倾向于实验性的东西,你可以看看Boost.Type Erasure,它删除了一些样板,但还不是正式版本的一部分。