不使用模板参数的 C++ 模板类方法
Posted
技术标签:
【中文标题】不使用模板参数的 C++ 模板类方法【英文标题】:C++ Template class methods that do not use template parameter 【发布时间】:2014-11-12 01:23:19 【问题描述】:我有一个具有 M 个方法的类,并且只有一个方法对 std::array 执行只读操作。其余的 M-1 方法不使用 std::array。代码如下。假设我不能打破这个班级。
我的担忧是:
-
这段代码有点难看,因为如前所述,只有一种方法使用参数 N。
如果我用不同的 N 实例化 Bar 100 次,那代码不会膨胀吗?就像我说的,只有 1 种方法使用参数 N,但我的理解是,我将获得 99*(M-1) 个有效相同方法的额外副本。
话虽如此,使用向量或 C 数组来避免模板是标准的吗?我会牺牲任何潜在的性能吗?
//bar.h
template<int N>
class Bar
public:
Bar(const std::array<Foo, N>& arr);
void method_one();
void method_two();
void method_three();
...
private:
const std::array<Foo, N> arr_;
;
template<int N> Bar<N>::Bar(const std::array<Foo, N>& arr) :
arr_(arr)
template<int N> void Bar<N>::method_one()
//....
template<int N> void Bar<N>::method_two()
//....
//etc
【问题讨论】:
如果您从不访问模板参数依赖类型,为什么还要选择它? 我想向类构造函数传递一个 std::array 并将它的副本存储为类成员。 其他函数是否访问该成员?如果没有,您可以使用继承。 您可以假设访问该成员的方法很少(上面我以 M 中的 1 个为例)。继承可能会解决这个问题,但听起来像是 hack。 这并不是真正的 hack,它也在标准库中完成(即使我们只看标准对<iostream>
的描述,更不用说任何实现的作用了)。
【参考方案1】:
首先,您的编译器可能(或可能被诱导)折叠相同的函数,即使它们具有不同的签名。 这是否合法(以及如何强制),请参见此处:
Do distinct functions have distinct addresses?Is an implementation allowed to site two identical function definitions at the same address, or not?
接下来,如果您的模板成员独立于模板参数,请考虑将它们移至基类:
class Bar_base
// Move everything here not dependent on template-arguments.
// Can be done multiple times if useful
template<int N> class Bar : public Bar_base
// Everything dependent on `N`, and maybe some using-declarations
// for proper overloading
标准库的所有实现都广泛使用它,如果您查看<iostream>
,它甚至被编入标准。
【讨论】:
【参考方案2】:如果只有构造函数使用 std::array<...> 您可以将模板类转换为具有模板构造函数的标准类。此外,我希望编译器足够聪明,不会复制 100 多个对 N 没有任何依赖关系的代码片段。
class Bar
public:
template<int N>
Bar(const std::array<Foo, N>& arr);
...
...
编辑:废话!!这似乎无法编译......它适用于像
这样的参数class Bar
public:
template<int N>
Bar(const int (& a)[N]);
【讨论】:
类成员arr_呢?我该如何申报? 我一起错过了 arr_。而且我的方法似乎甚至无法使用 std::array<...> 进行编译,尽管我经常将它用于固定大小的数组...叹息。以上是关于不使用模板参数的 C++ 模板类方法的主要内容,如果未能解决你的问题,请参考以下文章